ABOUT ME

-

Today
-
Yesterday
-
Total
-
  • Kotlin 기본 문법
    Kotlin 2019. 8. 3. 16:39

    타입 체크

    • if(true is Boolean)
    • if('a' is Char)

    타입 케스팅

    • Double to Int : double.toInt()
    • Int to Double : myInt.toDouble();
    • Char to Int : char.toInt()

    var, val 차이

    • var : 변경가능 변수
    • val : 변경불가 변수

    String pretty

        var logStr = """SELECT *
        FROM TABLE""";

    Compare

        "A".compareTo("B")

    String find, check

        val myString = "0123456789";
        println(myString.get(1));
        println(myString.subSequence(0,3))
        println(myString.contains("3"));

    Array

        // 배열 선언 (index 초기화)
        var sqArray = Array(5, { x -> x * x });
    
        // 기본 배열 선언
        var array2: Array<Int> = arrayOf(1,2,3);
    
        // 배열 선언 values
        var myArray = arrayOf(1, 2, 3, "ok");
    
        // get
        myArray[3]
        myArray.get(3)
        myArray.first()
    
        // get Index
        myArray.indexOf("ok")
    
        // replace value
        myArray[3] = "fail";
    
        // copy
        var copyArray = myArray.copyOfRange(0,1);
    
    

    Rang

    // orderBy ASc
        var onToTen = 1..10;
        var oneToTen2 = 1.rangeTo(10);
    
        // String range
        var alpha = "A".."Z";
    
        // orderBy Desc
        var tenToOne = 10.downTo(1);
    
        // step (jump)
        var range3 = oneToTen2.step(3);

    Opermiation

        if (age < 5) {
            println("Go to Preschool");
        } else if (age == 5) {
            println("Go to Kindergarten");
        } else if (5 > age && age <= 17) {
            var grade = age - 5
            println("Go to school");
        } else {
            println("do nothing")
        }
    
    
        when (age) {
            0, 1, 2, 3, 4 -> println("go to Preschool");
    
            5 -> println("Go to Kindergarten");
    
            in 6..17 -> {
                var grade = age - 5
                println("Go to school")
            }
    
            else -> println("do nothing")
        }

    loop

        for((index, value) in arrayOf(1,2,3).withIndex())

    function

    
    fun main(args: Array<String>) {
    
        fun add(num1: Int, num2: Int): Int = num1 + num2
        println(add(1, 2));
    
        // 매개변서명 지정하여 값넘기기
        fun subTract(num1: Int, num2: Int): Int = num1 - num2
        println(subTract(num2 = 3, num1 = 5));
    
        // 리턴타입없는 function
        fun sayHello(name: String): Unit = println("Hello ${name}");
        println(sayHello("Justin"))
    
        runApplication<KokotripApplication>(*args)
    
        // 여러개의 Value Return with Pair
        val (two, three) = nextTwo(1);
    
        println("1,  $two, $three")
    }
    
    // Paire을 쓰면 여러개의 value을 순서대로 넘길수 있다.
    fun nextTwo(num: Int): Pair<Int, Int> {
        return Pair(num + 1, num + 2);
    }
    
    
    
    // 여러개의 매개변수 넘기기 (vararg)
    fun main(args: Array<String>) {
        println(getSum(1, 2, 3, 4, 5))
    }
    
    fun getSum(vararg nums: Int): Int {
        var sum = 0;
        nums.forEach { n -> sum += n }
        return sum;
    }
    

    function 2 self 재귀함수

    fun fact(x: Int): Int {
        tailrec fun factTail(y: Int, z: Int): Int {
            if (y == 0) return z;
            else return factTail(y - 1, y * z)
        }
    
        return factTail(x, 1);
    }

    filter, reduce, fold, map, foreEach

        var numList = 1..20;
        var evenList = numList.filter { it % 2 == 0 }
        evenList.forEach { n -> println(n) }
    
        val numList2 = 1..2;
    
        // 초기값 없이 계
        val listSum = numList2.reduce { x, y -> x + y };
        println(listSum)
    
        // 초기값 셋팅후 계산
        val listSum2 = numList2.fold(1) { x, y -> x + y };
        println(listSum2)
    
        // any : Boolean
        val any = numList2.any { it % 2 == 0 };
        println(any);
    
        // map
        val map = numList2.map { it * 10 }
        println(map);

    function to create function

    val callbackFunction = makeMathFunc(10)
    println(callbackFunction(5));
    
    fun makeFunction(num1: Int): (Int) -> Int = { num2 -> num1 * num2 }
    

    function to parameter

    fun main(args: Array<String>) {
    
        val inputNum = 10;
    
        val (name, value) = mathOnList(inputNum, { num: Int ->
            num * inputNum;
        });
    
        println("$name : $value")
    }
    
    fun mathOnList(num: Int, myFunc: (num: Int) -> Int): Pair<String, Int> {
        return Pair("kim", myFunc(num));
    }

    MutableList (변경가능)

        var mutableList: MutableList<Int> = mutableListOf(1, 2, 3);
    
        mutableList.clear();
        mutableList.add(4);
        mutableList.remove(2);
        mutableList.removeAt(0);

    MutableMap (변경가능Map)

     var mutableMap2 = mutableMapOf<Int, Any?>(1 to "kim", 2 to "justin", 3 to "seunggab")
    
        var mutableMap = mutableMapOf<Int, Any?>()
        // map[Key] = value
        mutableMap[1] = "kim";
        mutableMap[2] = "justin";
        mutableMap.put(3, "seunggab")
    
        for((key, value) in mutableMap){
            println("$key : $value")
        }

    Class 생성

    fun main(args: Array<String>) {
    
        val justin = Animal("Justin", 20.0, 13.5);
        justin.getInfo();
        justin.height;
    
        var myDog = Dog("myDog", 20.0, 13.0, "Justin");
        myDog.getInfo();
    }
    
    
    open class Animal(val name: String,
                      var height: Double,
                      var weight: Double) {
        init {
            val regex = Regex(".*\\d+.*")
    
            require(!name.matches(regex)) { "Animal name Can't contain Numbers" }
            require(height > 0) { "Height must be greater then 0" }
            require(weight > 0) { "Weight must be greater then 0" }
    
    
        }
    
        open fun getInfo(): Unit {
            println("$name is $height tall and weights $weight");
        }
    }
    
    class Dog(name: String,
              height: Double,
              weight: Double,
              var owner: String) : Animal(name, height, weight) {
    
        override fun getInfo(): Unit {
            println("$name is $height tall and weights $weight and owner is $owner");
        }
    }

    interface

    fun main(args: Array<String>) {
    
        val myBird = Bird("tweety", true);
        myBird.fly(100.0);
    }
    
    
    interface Flyable {
        var flies: Boolean
        fun fly(distMile: Double): Unit
    }
    
    
    // Interface 내부 변수는 반드시 parameter 받는 부분에서 override 해야한다.
    class Bird constructor(
            val name: String,
            override var flies: Boolean = true) : Flyable {
    
        override fun fly(distMile: Double) {
            println("$name flies $distMile miles")
        }
    }

    null

      // error
        var nullVal: String = null;
    
        // null 가능
        var nullVal2: String? = null; 
    
        // return null 가능
        fun myFun(): String? = null;
    
        // null가능하기 떄문에 에러
        var nullVal3 = nullVal2.length;
    
        // 무조건 null이 아니다고 명시해준다 (!!)
        var nullVal4 = nullVal2!!.length;
    
        // elvis Null 아닐떄
        var nullVal5 = nullVal2 ?: 30;

    By 클래스 구현 유임

    불필요한 중복된 구현을 없애고 별도 커스텀하고 싶은 기능만 따로 구현하며, 기본적으로 부모의 기능을 그대로 사용한다.

    class CounterBy<T>(
            private val innerSet: MutableCollection<T> = HashSet<T>()
    ) : MutableCollection<T> by innerSet {
        var objectsAdded = 0;
        override fun add(element: T): Boolean {
            objectsAdded++;
            return innerSet.add(element);
        }
        override fun addAll(elements: Collection<T>): Boolean {
            objectsAdded += elements.size;
            return innerSet.addAll(elements);
        }
    }

    object

    싱글톤

    object Single {
        var container = HashMap<String, String>();
    
        fun add(map: HashMap<String, String>) {
            container = map;
        }
        fun get(key: String): String? {
            return container.get("key");
        }
    }

    동반객체 (companion object) 펙토리 패턴에 사용

    코틀린에는 static키워드가 없다. 대신해서 최상위 함수를 사용할수 있지만 때에따라 private으로 표시된 클래스 비공개 멤버에 접근할수 있다.
    그예가 팩토리패턴!! capanition object 클래스는 자신을 감싸고 있는 클래스의 모든 private을 접근할수 있다.

    class Sns private constructor(val nickName: String) {
        companion object { // companion object Loader 처럼 Alias을 붙힐수 있다.
            fun makeFacebook(id: String) = Sns("facebook_$id")
            fun makeGoogle(id: String) = Sns("google_$id")
        }
    }

    무명 내부 클래스

    fun countClick(window: Window) {
        window.addMouseListener(object : MouseAdapter() {
            // do something
        })
    }

    람다

    람다예제1

    val person1 = Person("first", 1, "man");
    val person2 = Person("second", 2, "man");
    
    val people = listOf<Person>(person1, person2);
    
    val maxOrigin = people.maxBy { p: Person -> p.age }
    
    // 괄호안 맨뒤 인자가 람다라면 밖으로 뺄수 있다
    val maxOrigin2 = people.maxBy() { p: Person -> p.age }
    
    // p의 타입을 생략할수 있다.
    val maxOrigin3 = people.maxBy() { p -> p.age }
    val max2 = people.maxBy(Person::age)
    val sum = { first: Int, second: Int -> first + second }
    
    // 결론으로 이렇게 간단하게 쓸수 있다.
    val max1 = people.maxBy { it.age }
    
    // 3가지 방법
    val maxOrigin10 = people.maxBy { p: Person -> p.age }
    val max10 = people.maxBy { it.age }
    val max20 = people.maxBy(Person::age)

    함수나, 프로퍼티도 값도 저장할수 있다.

    fun test2(){
            val sender = ::sendMail;
            sender("1", "2");
        }
    
    fun sendMail(first: String, second: String) {
        println("$first, $second")
    }

    Collection

    val list = listOf(1, 2, 3, 4, 5, 6, 7, 8, 9, 10);
    
    // filter 은 true을 반환하는 원소의 집합이다.
    val filtered = list.filter { it % 2 == 0 }
    var filtered2 = list.filter { p: Int -> p % 2 == 0 }
    println(filtered);
    println(filtered2);
    
    
    // map은 원소 값을 변경하여 새로운 컬렉션을 만든다.
    val multiple = list.map { it * 10 }
    val multiple2 = list.map { p: Int -> p * 10 }
    println(multiple)
    println(multiple2)
    
    
    val people = listOf(
            Person("firstName", 1, "male"),
            Person("secondName", 2, "male"),
            Person("thirdName", 3, "female"),
            Person("forthName", 4, "male"),
            Person("fifth", 5, "female")
    );
    
    
    // 원소의 일부 정보의 새로운 집한
    val names = people.map { it.name }
    val names2 = people.map(Person::name)
    val names3 = people.map { p: Person -> p.name }
    println(names)
    println(names2)
    println(names3)
    
    // 틀정 필터 조건의 이름
    val oldPeopleNames = people
            .filter { it.age > 4 }
            .map { it.name }
    println(oldPeopleNames);
    
    
    // 가장 나이가 많은 사람의 이름
    val olderPerson = people.maxBy { it.age }
    val older = people.filter { it == olderPerson }
            .map { it.name }
    println("olderName $older")
    
    
    // Map collection
    val numbersMap = mapOf(0 to "zero", 1 to "one", 2 to "two")
    val uppers = numbersMap
            .mapValues { it.value.toUpperCase() }
            .forEach { println(it) }
    println(uppers)
    
    
    val people = listOf(
        Person("firstName", 1, "male"),
        Person("secondName", 2, "male"),
        Person("thirdName", 3, "female"),
        Person("forthName", 4, "male"),
        Person("fifth", 5, "female")
    );
    
    /**
     * find
     * 리스트에서 해당하는 첫번째 원소를 리턴한다. 없으면 null
     * @return null | list
     */
    val find = people.find { it.name == "justin" }
    val firstOrNull = people.firstOrNull { it.name == "justin" }
    println("find : $find, firstOrNull : $firstOrNull");
    
    /**
     * any
     * 조건에 해당하는 원소가 하나라도 있는가?
     * @return true | false
     */
    val any = people.any { it.name == "justin" }
    println("any : $any")
    
    /**
     * all
     * 조건에 모든 원소가 해당하는지 true : false
     * @return true : false
     */
    val all = people.all { it.name != "" }
    println("all : $all")
    
    /**
     * groupBy
     * @return Map<Object, List<T>>
     */
    val groupBy = people.groupBy { it.age }
    println("groupBy : $groupBy")
    
    
    /**
     * flatMap
     * 여러 리스트를 하나의 리스트로 모은다.
     * String을ㅇ toList 하면 한글자씩 쪼개 리스트로 생성한다.
     * @return list
     */
    val flatMap = listOf("first", "second").flatMap { it.toList() }
    println("flatMap : $flatMap")
    
    
    /**
     * flatMap with toSet
     * List<Map<Object, List>> 리스트안에 존재하는 리스트를 단일 리스트로 반환
     * @return list
     */
    val peopleWithFriends = listOf(
            Person("firstName", 1, "male", listOf("a", "b")),
            Person("secondName", 2, "male", listOf("a", "b")),
            Person("thirdName", 3, "female", listOf("c", "b")),
            Person("forthName", 4, "male", listOf("a", "b")),
            Person("fifth", 5, "female", listOf("a", "d"))
    )
    
    val flatMapToSet = peopleWithFriends.flatMap { it.friends }.toSet()
    println("flatMapToSet : $flatMapToSet")

    sequence

    java의 stream과 같으며 stream을 지원하지 않는 버전을 위해 만드러짐

    /**
     * asSequence == stream 구버전에서 stream이 없는경우가 있어 sequence을 사용함
     * filter, map이 있을때 시퀀스가 없을땐 filter을 다수행하고, map 다수행하고 결과를 만들지만
     * sequence는 원소 하나가 기준이 되어 filter, map을 순차적으로 한번씩 수행한다.
     * @return toList을 해야지 새로운 리스트가 생성된다.
     */
    val list = listOf(1, 2, 3, 4, 5, 6, 7, 8, 9, 10)
    val asSequence = list.asSequence().filter { it % 2 == 0 }
            .map { it * 10 }
            .toList()
    println("asSequence : $asSequence")
    
    val asSequence2 = people.asSequence().firstOrNull { it.name == "firstName" }
    println("asSequence2 : $asSequence2");

    'Kotlin' 카테고리의 다른 글

    Kotlin Clock mockito  (1) 2021.11.10
    코틀린 기본요소  (2) 2019.03.20
    코틀린 프로젝트 생성 및 실행  (0) 2019.03.20
    코틀린 소개  (1) 2019.03.17

    댓글

Designed by Tistory.