일단 int는 primitive data type이라서 generic으로 포함될수 없다.

int는 wrapper를 써서 Integer가 되어야 하고... 

 

두가지 방법이 있다.

 

1. 반복문을 통해서 하나하나 넣어주기

int[] arr = {1, 2, 3};
List<Integer> list = new ArrayList<>(arr.length);
for (int num : arr) {
    list.add(num);
}

배열의 element하나씩 list 에 add해준다.

 

2. stream을 이용하는 방법

List<Integer> list1 = Arrays.stream(arr).boxed().collect(Collectors.toList());
List<Integer> list2 = IntStream.of(arr).boxed().collect(Collectors.toList());

먼저 Arrays.stream(arr)을 통해 배열을 stream 화 해준다. Arrays.stream(arr)의 결과는 IntStream 이므로 IntStream.of(arr)도 무방하다.

boxed() 를 통해서 stream의 개별 값을 wrapper 하여 Integer 객체로 변경한다.

collect를 통해서 List로 모아준다.

때는 2002년 3월, 대학교 2학년 때 이다. 컴퓨터 공학 전공으로 전공필수 과목으로 처음 Data Structure를 접했다.

당시 1학년 2학기 때, C 언어를 막 배운 상태였고, 2학년 올라오자마자 자료구조를 배우는데 java언어를 통해 배웠다.

당시에는 java 1.2 였던걸로 기억하는데, 정확하지는 않다.

 

아무튼 아무것도 모르는 학부 2학년인데, 갑자기 Stack이니, Queue 이니, Linked List 이니 알수 없는 단어를 쏟아내는 과목이 매우 버거웠다. (2학년때는 공부를 열심히 하지도 않았다!!!)

 

당시에는 이 과목의 필요성이나, 여기서 작성하는 프로그램들이 무엇을 하는것인지 이해할수가 없었고, 숙제로 구현해 오라고 하는데, 대체 무엇을 구현하는 지 조차 알수가 없었다.

당연히 성적은 잘 나오지 않았고, 나에겐 뭔가 숙제 같은 과목이 되었다.

 

나중에 군대다녀오고 복학후에 다시 재수강을 하긴 하였지만, 사실 재수강때 기억은 나질 않는다.

 

지금 다시 그때 과목을 배운다면 참 재밌게 배웠겠다는 생각이 들고, 또 개발자로 10년을 지냈지만 여전히 사용한다는 점에서 매우 중요했던 과목이라고 생각을 하게 되었다.

 

당시에 공부 하던 책을 꺼내보았다.

 

https://www.amazon.ca/Data-Structures-Algorithms-Michael-Goodrich/dp/0471383678

짠! 이책이다..  무려 하드커버...

 

지금부터 여기에 나와있는 자료구조들을 하나하나 구현해보고자 한다.

 

 

 

Data Structure Implement Description
Stack https://ijeee.tistory.com/30 https://github.com/jeng832/DataStructure/tree/master/Stack

Queue

https://ijeee.tistory.com/31 https://github.com/jeng832/DataStructure/tree/master/Queue

Linked List

   

Double-Ended Queue

   

Vector

   

List

   

Sequnce

   

Iterator

   

Tree

   

Binary Tree

   

Priority Queue

 

   

Heap

   

Dictionary

   

Hash

   

Ordered Dictionary

   

Binary Search Tree

   

AVL Tree

   

Multi-Way Search Tree

   

(2,4) Tree

   

Red-Black Tree

   

Graph

   

Directed Graph

   

Weighted Graph

   

많기도 하다...-_- 다할수 있을까?;;;;;

 

'Development > Data Structure' 카테고리의 다른 글

Data Structure 에 대한 기억  (0) 2020.08.23
Queue  (0) 2020.08.23
Stack  (0) 2020.06.20

Queue는 LIFO(Last In First Out) 구조로 data를 저장할 수 있는 자료 구조 이다.

Queue는 쉽게 생각하면, 줄서기를 생각할 수 있다.

먼저 저장된(enqueue)된 data는 먼저 빼낼수 있다(dequeue)

 

또한 front() method를 이용하여 Dequeue() 대상이 되는 현재 Queue안에 있는 data 중 가장 먼저 저장된 data가 무엇인지 알수 있다.

 

Queue의 interface는 아래와 같다.

public interface Queue {
    public int size();
    public boolean isEmpty();
    public boolean isFull();
    public Object front();
    public void enqueue(Object elem);
    public Object dequeue();
    public String printQueue();
}

 

Queue는 배열 혹은 List로 구현 할 수 있다.

 

실제 구현은 아래 링크를 참조

 

https://github.com/jeng832/DataStructure/tree/master/Queue

'Development > Data Structure' 카테고리의 다른 글

Data Structure 에 대한 기억  (0) 2020.08.23
Queue  (0) 2020.08.23
Stack  (0) 2020.06.20

1. LIFO구조의 Data Structure, Stack

- push(), pop() 등의 명령어로 Last In First Out 구조를 가지고 data를 저장 할 수 있는 자료 구조

 

2. Stack의 구조 및 interface

가. Stack의 구조

Stack

나. Stack의 interface

public interface Stack {
    public int size();

    public boolean isEmpty();

    public Object top();

    public void push(Object element);

    public Object pop();

    public String printStack();

    public boolean isFull();
}

- 저장은 push()를 통해서 이루어지고, push된 data는 Stack의 제일 상단(top)에 저장

- 저장된 data를 가져올때는 pop()을 사용하고 top에 위치한 data를 가져오며, pop() 된 data는 Stack에서 삭제

- isEmpty(), isFull(), size()를 통해 Stack의 현재 상태 확인 가능

 

 

실제 구현은 아래 github 링크를 통해 확인 가능

https://github.com/jeng832/DataStructure/tree/master/Stack

 

jeng832/DataStructure

Contribute to jeng832/DataStructure development by creating an account on GitHub.

github.com

 

'Development > Data Structure' 카테고리의 다른 글

Data Structure 에 대한 기억  (0) 2020.08.23
Queue  (0) 2020.08.23
Stack  (0) 2020.06.20

Gson 을 이용하여 JsonUtil을 만들어 보았다.

object mapping 과 object to Json

JsonObject 혹은 Json String에서 값 얻어오기 등 지원

https://github.com/jeng832/blog-example/tree/master/JsonUtil

JsonUtil

method list

public static T fromJson(String json, Class clazz)

  • object mapping from Json String to class

public static String toJson(T obj)

  • class to Json String

public static JsonObject parse(String json)

  • Json String to JsonObject

public static String getValue(JsonObject object, String key)

  • get String value of key from JsonObject
  • Support chained key
    • key1.key2.key3
  • Support array index
    • arrKey[10]
    • arrKey[0][2]
  • It can throw NumberFormatException, IndexOutOfBoundsException

public static String getValue(String jsonStr, String key)

  • get String value of key from Json String

public static int getValueAsInteger(String jsonStr, String key)

  • get int value of key from Json String

public static int getValueAsInteger(JsonObject jsonObj, String key)

  • get int value of key from JsonObject

public static long getValueAsLong(String jsonStr, String key)

  • get long value of key from Json String

public static long getValueAsLong(JsonObject jsonObj, String key)

  • get long value of key from JsonObject

public static double getValueAsDouble(JsonObject jsonObj, String key)

  • get double value of key from JsonObject

public static double getValueAsDouble(String jsonStr, String key)

  • get double value of key from Json String

public static float getValueAsFloat(JsonObject jsonObj, String key)

  • get float value of key from JsonObject

public static float getValueAsFloat(String jsonStr, String key)

  • get float value of key from Json String

public static boolean getValueAsBoolean(String jsonStr, String key)

  • get boolean value of key from Json String

public static boolean getValueAsBoolean(JsonObject jsonObj, String key)

  • get boolean value of key from JsonObject

public static boolean contain(String jsonStr, String key)

  • check the key is in the Json String

public static boolean contain(JsonObject jsonObj, String key)

  • check the key is in the JsonObject

https://github.com/jeng832/blog-example/tree/master/gson2

 

jeng832/blog-example

Contribute to jeng832/blog-example development by creating an account on GitHub.

github.com

Gson은 Object mapping 방식 말고도, Json자체를 JsonObject라는 class로 만들어서 Json내에 object, 값, 배열,null 을 가져오거나, 추가, 삭제 등을 할 수 있다.

 

먼저 JsonObject에서는 Json의 요소를 구분하는 총 5가지 종류의 class가 있다.

JsonElement, JsonObject, JsonPrimitive, JsonArray, JsonNull

 

1. JsonElement

위의 다섯가지 중 JsonElement를 제외한 4가지는 JsonElement를 상속한다.

즉, JsonElement는 나머지 4가지의 부모class로 추상클래스로 정의되어 있다.

기본적으로 getter를 통해서 Json의 요소를 가져오면 기본적으로 JsonElement 형태로 받아오며, 필요에 따라서 적절히 변환해서 사용해야 한다.

 

2. JsonObject

Json에서 중괄호로 묶여서 하나의 Object를 나타낼때, 그것을 표현하기 위한 class

당연히 key-value형태로 존재하며, 실제 구현은 LinkedTreeMap으로 구현되어 있다.

 

3. JsonPrimitive

Json에서 특정 key의 value값을 나타내기 위한 class, 

숫자, 문자, Boolean 등 의 실제 값을 저장한다.

 

4. JsonArray

Json에서 [] 로 묶여서 배열을 나타내기 위한 class

index로 접근 가능하며, 실제 List와 유사하다.(알고보니 구현체도 ArrayList로 구현되어 있군...)

 

5. JsonNull

null object를 표현하기 위한 class

 

아래 Test code를 이용해서 확인 가능하다..

public class GsonTest {
    @Test
    public void testJsonObject() {
        String json =
                "{" +
                "    strKey : strValue, " +
                "    numKey: 235, " +
                "    arrKey: [arrV1, arrV2, arrV3]," +
                "    objKey: {subKey: subValue}," +
                "    numArrKey: [100, 200, 300]," +
                "    nullKey: null" +
                "}";
        JsonObject jsonObj = (JsonObject) JsonParser.parseString(json);
        System.out.println(jsonObj.isJsonPrimitive());
        System.out.println(jsonObj.isJsonObject());
        System.out.println(jsonObj.isJsonArray());
        System.out.println(jsonObj.isJsonNull());
        System.out.println(jsonObj.toString());

        System.out.println("=============== strKey ===============");
        JsonElement element = jsonObj.get("strKey");
        System.out.println(element.isJsonPrimitive());
        System.out.println(element.isJsonObject());
        System.out.println(element.isJsonArray());
        System.out.println(element.isJsonNull());
        System.out.println(element.toString());

        System.out.println("=============== numKey ===============");
        element = jsonObj.get("numKey");
        System.out.println(element.isJsonPrimitive());
        System.out.println(element.isJsonObject());
        System.out.println(element.isJsonArray());
        System.out.println(element.isJsonNull());
        System.out.println(element.toString());

        System.out.println("=============== arrKey ===============");
        element = jsonObj.get("arrKey");
        System.out.println(element.isJsonPrimitive());
        System.out.println(element.isJsonObject());
        System.out.println(element.isJsonArray());
        System.out.println(element.isJsonNull());
        System.out.println(element.toString());

        System.out.println("=============== objKey ===============");
        element = jsonObj.get("objKey");
        System.out.println(element.isJsonPrimitive());
        System.out.println(element.isJsonObject());
        System.out.println(element.isJsonArray());
        System.out.println(element.isJsonNull());
        System.out.println(element.toString());

        System.out.println("=============== nullKey ===============");
        element = jsonObj.get("nullKey");
        System.out.println(element.isJsonPrimitive());
        System.out.println(element.isJsonObject());
        System.out.println(element.isJsonArray());
        System.out.println(element.isJsonNull());
        System.out.println(element.toString());
    }
}

 

실행 결과는...

false
true
false
false
{"strKey":"strValue","numKey":235,"arrKey":["arrV1","arrV2","arrV3"],"objKey":{"subKey":"subValue"},"numArrKey":[100,200,300],"nullKey":null}
=============== strKey ===============
true
false
false
false
"strValue"
=============== numKey ===============
true
false
false
false
235
=============== arrKey ===============
false
false
true
false
["arrV1","arrV2","arrV3"]
=============== objKey ===============
false
true
false
false
{"subKey":"subValue"}
=============== nullKey ===============
false
false
false
true
null  

기본적으로 Json String을 JsonObject로 받기 위해서는 JsonParser.parseString() method를 이용해야 한다.

(해당 method는 static이므로, 걍 사용하면 된다.)

참고로 parseString의 return 은 JsonElement 이므로 변환해야 JsonObject로 받을 수 있다.

    @Test
    public void testJsonParse() {
        String json =
                "{" +
                        "    strKey : strValue, " +
                        "    numKey: 235, " +
                        "    arrKey: [arrV1, arrV2, arrV3]," +
                        "    objKey: {subKey: subValue}," +
                        "    numArrKey: [100, 200, 300]," +
                        "    nullKey: null" +
                        "}";
        JsonObject jsonObj = (JsonObject) JsonParser.parseString(json);
        jsonObj = JsonParser.parseString(json).getAsJsonObject();
    }

 

코드를 보면 알 수 있듯이 get("key")을 통해서 얻어온 값은 JsonElement이고 이를 isJsonXXX() 를 통해서 어떤 종류인지 확인 한후 getAsXXX()을 통해 변환후 사용해야 한다.

    @Test
    public void testJsonConvert(String json) {
        JsonElement elem = JsonParser.parseString(json);
        if (elem.isJsonPrimitive()) {
            JsonPrimitive primitive = elem.getAsJsonPrimitive();
            // logic for JsonPrimitive
        } else if (elem.isJsonArray()) {
            JsonArray array = elem.getAsJsonArray();
            // logic for JsonArray
        } else if (elem.isJsonObject()) {
            JsonObject object = elem.getAsJsonObject();
            // logic for JsonObject
        } else if (elem.isJsonNull()) {
            JsonNull jsonNull = elem.getAsJsonNull();
            // logic for JsonNull
        }
    }

 

개발을 하다보면 json을 통해서 정보전달을 하는 경우가 많다. 그 때 gson, jackson 등 여러가지가 library를 취향껏 사용하면 되는데, 오늘은 google에서 나온 gson을 이용한 object mapping을 설명하겠다.

 

1. gradle에 gson 추가

먼저, gson 을 사용하기 위해서 gradle에 추가해야 한다.

최신 gson은 아래 링크를 통해 확인 가능하고..

https://mvnrepository.com/artifact/com.google.code.gson/gson

 

Maven Repository: com.google.code.gson » gson

 

mvnrepository.com

이 글을 쓰는 현재 최신 버젼인 2.8.6을 활용 한다.

 

compile group: 'com.google.code.gson', name: 'gson', version: '2.8.6'

 

추가 하고 gradle sync 를 하면 완료

 

2. class 만들기

json을 class로 만들거나, class를 json으로 object mapping 시키기 위해서 우선 대상 class를 만든다.

간략히 아래와 같이 생성...

toString()은 확인을 위해 만든거라서 없어도 무방하다..

 

public class Animal {
    private int nLeg;
    private String name;

    @Override
    public String toString() {
        return "Animal[nLeg: " + nLeg + ", name: " + name + "]";
    }
}

 

3. Object mapping 하기

object mapping을 하기 위한 method는 2가지, fromJson / toJson 이다.

json -> object 는 fromJson

object -> json 은 toJson

 

매우 간단하다.

 

code로 보면 아래와 같다...

String에서 " 큰따옴표를 사용하려면 \" 를 사용해야 함을 유의!!

public class AnimalTest {

    @Test
    public void testJson() {
        Gson gson = new Gson();

        String json = "{\"nLeg\":4, \"name\": \"Bill\"}";
        Animal animal = gson.fromJson(json, Animal.class);
        System.out.println(animal);

        String reJson = gson.toJson(animal);
        System.out.println(reJson);
    }
}

 

결과는?

 

Animal[nLeg: 4, name: Bill]
{"nLeg":4,"name":"Bill"}

 

4. key 이름 변경

본인은 헝가리안 표기법을 좋아하지는 않지만, 개발조직의 coding convention상 m 이나, n 혹은 i 등을 prefix로 사용하여 class의 멤버이름을 설정해 주어야 하는 경우가 있다.

gson을 그냥 활용할 경우 class의 멤버 이름을 그대로 json의 key로 mapping 시키기 때문에, 위의 예제에 nLeg 같은 key를 사용해야 한다. 

멤버의 이름 말고 json key이름을 지정하는 방법은 gson에서 제공하는 annotation으로 해결 가능하다.

사용할 annotation은 @SerializedName("key 이름")

 

2번의 class를 아래와 같이 수정 하고 

 

import com.google.gson.annotations.SerializedName;

public class Animal {
    @SerializedName("legs")
    private int nLeg;

    @SerializedName("name")
    private String name;

    @Override
    public String toString() {
        return "Animal[nLeg: " + nLeg + ", name: " + name + "]";
    }

}

 

3번의 test code에서 json 의 key이름을 수정하여 다시 실행 해보면...

 

public class AnimalTest {

    @Test
    public void testJson() {
        Gson gson = new Gson();

        String json = "{\"legs\":4, \"name\": \"Bill\"}";
        Animal animal = gson.fromJson(json, Animal.class);
        System.out.println(animal);

        String reJson = gson.toJson(animal);
        System.out.println(reJson);
    }
}

legs 를 key로 사용해도 nLeg 변수에 값이 들어가고, 해당 class를 다시 json 화 했을 때도 지정한 key인 legs 로 바뀌는 것을 알 수 있다.

Animal[nLeg: 4, name: Bill]
{"legs":4,"name":"Bill"}

 

위의 code는 아래 github에서 확인 가능하다.

https://github.com/jeng832/blog-example/tree/master/gson

mongodb 시작하기

$ sudo service mongod start

 

mongodb shell 시작

$ mongo

 

database 종류 확인

> show databases

 

database 사용(선택)

> use {database이름}

 

collection 종류 확인

(db 선택 이후)

> show collections

 

collection 제거

> db.{collection 이름}.drop()

 

document 추가

> db.{collection 이름}.insert({문서})

db.books.insert({"a":1})
WriteResult({ "nInserted" : 1 })

 

document bulk insert

> db.{collection 이름}.insert([{문서}])

db.books.insert([{"a":1},{"b": 1}])
BulkWriteResult({
"writeErrors" : [ ],
"writeConcernErrors" : [ ],
"nInserted" : 2,
"nUpserted" : 0,
"nMatched" : 0,
"nModified" : 0,
"nRemoved" : 0,
"upserted" : [ ]
})

 

document 찾기

> db.{collection 이름}.find({조건})

{조건}도 json 형태로 입력

 

document 지우기(조건 맞는 모든 document 지우기)

> db.{collection 이름}.remove({조건})

{조건}도 json 형태로 입력

 

document 지우기(조건 맞는 하나의 document 지우기)

> db.{collection 이름}.remove({조건}, true)

{조건}도 json 형태로 입력

'Development > Database' 카테고리의 다른 글

MongoDB 기본 명령어  (0) 2019.10.19
MongoDB에서 Connection Pool 구성 하기  (0) 2017.02.13
MongoDB Ubuntu에 설치하기  (0) 2017.02.10
MongoDB 에서 admin 만들기  (2) 2017.02.10

Kotlin에서 Class 선언 하는 방법에 대해서 포스팅을 했으니

Kotlin에서 Class 선언하기

 

Kotlin에서 Class 선언하기

Kotlin(코틀린)은 JetBrains에서 제작된 프로그래밍 언어로서 구글에서 Android 기본 언어로 채택 되면서 주목받는 hot한 언어가 되었다. JetBrains의 연구소가 있는 러시아 상트페테르부르크에 있는 코틀린 섬에..

ijeee.tistory.com

이번에는 Class 생성자(Constructor)에 대해서 포스팅 해보겠다.

 

Kotlin의 생성자는 주생성자(Primary Constructor)와 부생성자(Secondary Constructor)로 구분된다.

 

1. 주생성자

Kotlin을 배우면서 느낀점은 Java 개발자가 개발하면서 느꼈던 온갖 귀찮은 작업을 생략하는 언어라는 느낌이다-_-);;;

귀찮은 Java 개발자의 언어랄까......

 

 

Java에서는 모든 생성자는 method처럼 선언을 해주어야 한다 하지만 Kotlin에서는 그런 귀찮은 일을 하지 않아도 된다!!

주생성자는 class 선언하면서 생성자를 동시에 정의할 수 있는 기법이다.

방법은 class 이름 옆에 생성자의 parameter를 받고, Property 선언시

해당 값을 이용하여 초기화 해주면 된다.

 

class Animal(_nLeg:Int, _color:String) {
    val nLeg:Int = _nLeg
    val color:String = _color
    var name:String = "Tom"

    fun eat(something:String) {
        println("Eat $something")
    }

    fun cry() {
        println("Cry!!!")
    }
}

이제 Class를 사용하려면 아래와 같이 주생성자의 인자를 넘겨주어야 한다.

val myAnimal = Animal(4, "yellow")

자 이제 귀찮은 Java 개발자를 위해 한번더 생략!

생성자의 인자도 선언해줘야 하고 Property도 선언해줘야 하는데, 귀찮으니 한방에 쓰자!!!

 

생성자의 인자를 적어줄때 val, var을 적으면, 해당 인자가 바로 class의 property가 된다.

이 글을 보는 사람이라면 알겠지만 val은 불변, var은 변화가 가능한 Property

class Animal(val nLeg:Int, val color:String) {
    var name:String = "Tom"

    fun eat(something:String) {
        println("Eat $something")
    }

    fun cry() {
        println("Cry!!!")
    }
}

예제에서 보다시피 생성자를 통해서 초기화 하기 싫은 변수는 주생성자의 인자로 넣지 않고 따로 선언할 수 있다.

그런데 실제 개발을 하다보면 생성자에서 변수 초기화만 하지 않고 뭔가 로직을 넣어야 하는 상황이 오는데,

주생성자가 Class이름과 함께 정의를 하게된다면...

로직은 어떻게 넣을까???

 

Kotlin에서는 주생성자의 추가 로직을 위해 init이라고 하는 키워드를 통해 초기화 블록을 제공한다.

class Animal(val nLeg:Int, val color:String) {
    var name:String = "Tom"
    init {
        println("=== Primary Init block ===")
        println("nLeg: $nLeg, color: $color, name: $name")
        // Do something!!
    }

    fun eat(something:String) {
        println("Eat $something")
    }

    fun cry() {
        println("Cry!!!")
    }
}

 

2. 부생성자

부생성자는 Java의 생성자와 유사하다. 여러개의 생성자를 만들수 있고 생성자에서 어떤 동작을 할지 정의를 해주어야 한다.  부 생성자임을 알려주는 키워드는 constructor

단, 부생성자는 반드시 주생성자와 같이 사용되어야 한다. 부생성자는 주생성자를 호출한다.

class Animal(val nLeg:Int, val color:String) {
    var name:String = "Tom"
    init {
        println("=== Primary Init block ===")
        println("nLeg: $nLeg, color: $color, name: $name")
        // Do something!!
    }

    constructor(_nLeg:Int, _color:String, _name:String) : this(_nLeg, _color) {
        println("=== Secondary constructor start ===")
        this.name = _name
        println("=== Secondary constructor end ===")
    }

    fun eat(something:String) {
        println("Eat $something")
    }

    fun cry() {
        println("Cry!!!")
    }
}

부생성자 선언 뒤에 : this()를 통해서 주생성자의 인자를 전달해주어야 한다.

부생성자를 호출하게 되면 주생성자와 초기화 블록의 순서는 어떻게 될까??

val myAnimal = Animal(4, "yellow", "Smith")

 

=== Primary Init block ===
nLeg: 4, color: yellow, name: Tom
=== Secondary constructor start ===
=== Secondary constructor end ===

실행 결과에서 알수 있듯이 주생성자 -> 초기화 블록 -> 부생성자 순서로 호출된다.

 

포스팅에 사용된 소스는 아래의 github에서 확인 가능하다.

 

https://github.com/jeng832/blog-example/tree/master/24_Kotlin%20class%20constructor%20%EC%A0%95%EB%A6%AC

IntelliJ에서 Kotlin으로 작성된 소스를 Java 코드로 확인할 수 있다.

Decompiler 기능을 이용한 것인데..

 

Tools > Kotlin > Show Kotlin Bytecode 선택

Kotlin Bytecode 탭(?)에서 Decompile 버튼 클릭

 

Decompile 된 java 소스 확인

+ Recent posts