fun main(args: Array<String>) {
println("Hello, world!")
}
- fun: 함수임을 나타내는 키워드
- main: 함수 이름 ( 여기서는 엔트리포인트가 되는 메인 함수)
- class 필요 없음 – 탑 레벨 함수 정의 가능.
- (args: Array<Sting>): 함수인자 "변수명: 타입"
- println("Hello, world!"): System.out.println을 println으로 간단하게 사용표준 자바 라이브러리 함수를 간소화해주는 wrapper를 제공
- ; (세미콜론) 불필요
* 이후 예제는 안드로이드 스튜디오에서…
현재 안드로이드 스튜디오에서 직접 코틀린 메인 실행 안됨. (버그)
실제 안드로이드 예제전까지 유닛테스트의 테스트로 예제 실행
# Kotlin 파일
- 일반 파일과 클래스 파일
• 코틀린 프로그램은 확장자가 kt인 파일
• 파일(File)과 클래스 파일(Class) 편의상 구분
- Java 와 같이 파일 이름과 class 이름이 같은 경우 class 파일로 인식
- 패키지는 java 와 다르게 실 경로와 맞지 않아도 가능. 그러나 가능한 실 경로와 맞게 해주는것이 편리함
# Kotlin 변수
- 변수 선언
• val(혹은 var) 변수명 : 타입 = 값
• val (value)는 Assign-once 변수 → 값이 변하지 않기 때문에 setter 없음
• var (variable)은 Mutable 변수 → setter 있음
• 타입 추론 지원 (타입 생략 가능)
- 변수 초기화
• 변수 선언은 최상위(클래스 외부), 클래스 내부, 함수 내부에 선언
* 최상위 레벨이나 클래스의 멤버 변수는 선언과 동시에 초기화 (예외 : lateinit)
• 함수 내부의 지역변수는 선언과 동시에 초기화 필요 없음
• 기본적으로 null 대입이 허용되지 않지만 ? 을 이용하면 허용
ex) var str String ?= null
• """ 으로 멀티라인 스트링 대입 가능
- 문자열 템플릿으로 사용 가능
var s1=“s1”
println(“s1=$s1”)
- 코틀린에서 변수는 프로퍼티(property) : getter, setter로 접근
- val로 선언한 변수의 초기값을 변경할 수는 없지만, 일반적인 상수변수와 다름 → 단지 setter 가 없는, 바꿀 수 없는 것
- const라는 예약어를 이용해 상수 변수 선언
- 최상위 레벨에서 선언할 때만 const 예약어 사용 가능
var <propertyName>[: <PropertyType>] [= <property_initializer>]
[<getter>]
[<setter>]
* [] 부분은 생략 가능(자동으로 추론됨)
* getter, setter 는 기본적으로 만들어지지만, 재정의할 수 있음.
val topData1: Int//error
var
topData2:
Int//error
const var topData3: Int//error
const val topData4: Int = 10
var
str: String = "aaa" // ok
var
str2
= "bbb" // 타입 추론에 의해 ok
var
str3: String = null // error
var
str4: String? = null // ok
var
str5
= """ // ok
abde
efg
high
""".trimIndent()
class
User
{
val objData1: String//error
var objData2: String//error
fun some(){
val localData1: Int//ok...
var localData2: String//ok...
println(localData1)//error
localData2="hello"//ok...
println(localData2)//ok...
}
}
# Kotlin - Null 처리하는 방법
- 디폴트는 null 허용되지 않음. 하지만 ? 을 이용하면 null이 허용됨.
① ?. 연산 : if(a != null) a.length
fun getFirstChar(text: String?): Char? {
return text?.get(0) // text가 null이면 get 메서드는 호출되지 않으며, get의 리턴 값도 null이 된다.
}
fun getTextOf(editText: EditText?): String? {
return editText?.getText()?.toString() // 둘 중 하나라도 null 이면 null 리턴
}
② !! 연산
• 간혹 변수가 null 값이 아님이 확실한데도 Nullable로 선언된 경우(특히 Java로 정의된 메서드에 접근할 때) 변수의 이름 뒤에 !!를 붙여 Non-Null 타입으로 강제 캐스팅
• !!로 캐스팅한 변수가 null이었다면 NullPointerException이 발생
fun onCreateView(inflater: LayoutInflater?, container: ViewGroup?, savedInstanceState: Bundle?): View? {
// inflater는 Non-Null임이 확실한 상태. !!을 붙여 LayoutInflater로 강제 캐스팅한다.
inflater!!.inflate(R.layout.fragment_statistics, container)
return super.onCreateView(inflater, container, savedInstanceState)
}
③ ?: 연산(앨비스 연산) : Kotlin에는 삼항연산자 없음.
fun function(param: Map<String, String>) {
// 만약, param.get("key")의 값이 null이면 ?: 오른쪽에 있는 "default value"가 value에 대입된다.
val value = param.get("key") ?: "default value"
}
④ as 연산자(캐스팅 연산자)
• 캐스팅 불가능한 경우 ClassCastException 발생
• as? 연산자는 ClassCastException이 발생해야 하는 상황에 에러 발생 없이 Null 리턴
# Kotlin - lateinit, lazy
- lateinit : 초기화 지연 프로퍼티(Late-initialized property). modifier
lateinit var lateT01:String
* 나중에 함수의 로컬영역에서 꼭 초기화 시킨 후 실행시켜야함.
- lazy : 초기화 지연시킬 때 사용. 람다를 파라미터로 받고 Lazy<T> 인스턴스를 반환
val lazyT01: String by lazy {
println("Hello lazyT01")
"abde"
}
* println(lazyT01) 해보면 Hello lazyT01, abde 가 순서대로 나온다.
- 둘의 차이점
• lateinit은 var 타입만 가능하고 lazy는 val 타입만 가능
• lateinit은 primitive type은 불가능하나 lazy는 가능
• lateinit은 Non-null 타입만 가능하나 lazy는 둘 다 가능
• lateinit은 로컬 변수에서는 불가능 하나 lazy는 가능
# Kotlin - 숫자 타입
- Int, Double 등은 클래스이며 이 클래스로 타입을 명시하여 선언한 변수는 그 자체로 객체
Type
|
Bit width
|
Double |
64 |
Float - f |
32 |
Long - L |
64 |
Int |
32 |
Short |
16 |
Byte |
8 |
* -f, -L : 자동으로 타입 추론 가능
- 코틀린의 숫자 타입의 클래스들은 모두 Number 타입의 서브 클래스
- 문자(Characters)는 Number Type이 아니다.
- Number Type에 대한 자동 형 변형(implicit conversions for number)을 제공하지 않는다. : ToXXX() 변환 함수 사용
- 숫자 타입에 대입되는 데이터에 언더바(Underscore) 추가 가능(가독성 Up!)
ex) val oneMillion: Int = 1_000_000
# Kotlin - 논리, 문자, 문자열타입
val isTrue1: Boolean = true && false
val isTrue2:
Boolean = true
||
false
val isTrue3:
Boolean = !true
val charData='C'
var
charData2:Char ='C'
var
str0:
String = "Hello"
# Kotlin - Any, Unit, Nothing 타입
- 코틀린 클래스의 최상위 클래스는 Any (Java의 Object 느낌)
- Unit : 기본 리턴 (java 의 void 느낌), 생략 가능
- Nothing : 의미 있는 데이터가 없다는 것을 명시적으로 선언하기 위해 사용하는 타입
• return 타입이나 인자로만 사용
• 리턴도 없고, 호출코드로 복귀하지 않을 때 사용 가능
# Kotlin - collection 타입
타입 |
함수 |
특징 |
|
List |
List |
listOf() |
Immutable |
MutableList |
mutableListOf() |
mutable |
|
Map |
Map |
mapOf() |
Immutable |
MutableMap |
mutableMapOf() |
mutable |
|
Set |
Set |
setOf() |
Immutable |
MutableSet |
mutableSetOf() |
mutable |
Iterator “ hasNext() 함수와 next() 함수를 이용해 순차적 이용
val list1=
listOf<String>("hello","list")
val iterator1=list1.iterator()
while (iterator1.hasNext()){
println(iterator1.next())
}
# Kotlin - is, as
- is (!is) : java 에서의 instanceof. true 또는 false 리턴
fun getStringLength(obj: Any): Int? {
if (obj is String) {
// 'obj' is automatically cast to 'String' int this branch
return obj.length
}
// 'obj' is still of type 'Any'
// Type이 String이 아니라서 null을 return 하게 됩니다.
return null
}
- as (as?) : 타입 캐스팅
• val x: String? = y as? String // 캐스팅에 실패할 경우 Exception이 발생하지 않고 x에 null값이 대입된다.
• 별칭으로도 사용 ex) import MotorCycle.Engine as engine
# Kotlin - 함수
- 함수 선언
• fun 함수명(매개변수명 : 타입) : 리턴타입 { }
• 매개변수에는 var, val 선언불가 (클래스 primary 생성자는 var, val 사용 가능)
• 의미있는 반환값이 없을 때는 Unit (void) – 생략가능
• 탑레벨 함수 선언 가능
• 함수내에 함수(지역함수) 선언 가능
• Class 안의 멤버 함수 선언 가능 -> Java로 디컴파일 해보면 클래스 내 static 메소드로 생성됨
• 함수 오버로딩 가능 -> open 해줘야함(?)
• 기본 인수(default parameter)와 명명된 인수(원하는 parameter) 사용 가능
• 확장함수 가능 : 이미 만들어진 클래스를 확장해서 메소드를 만들 수 있음
fun Int.addex(){
~~~~~~~~~
}
1.addex()
• Infix 로 중위 표현식을 함수 호출에도 사용이 가능 ex) a add b
* 클래스의 맴버 함수로 선언되거나 혹은 클래스의 extension 함수인 경우
* 하나의 매개변수를 가지는 함수의 경우
• 가변인수 : vararg, 함수의 파라미터가 몇 개가 될지 모를 때
• 재귀함수
* Tailrec 꼬리재귀함수 가능 : 재귀함수로 컴파일하는 것이 아닌 while문으로 컴파일 하여 최적화(stack overhead 발생 줄임), 사용 가능한 조건 있음(예를 들면 끝이 있다던지!)
• 제너릭 함수 가능 : 타입을 parameter로 넘길 수 있음
• 람다 함수 가능 : 함수를 식으로 만들 수 있음
• 하이 오더 function(고차함수) 가능 : 함수를 parameter로 사용 가능
fun
some(a: Int, b: Int): Int
{
return
a + b
}
fun some(a: Int,
b: Int): Int = a + b
fun some(a: Int,
b: Int) = a + b
fun sayHello(name:
String = "kkang", no:
Int){
println("Hello!!"+name)
}
fun
main(args:
Array<String>) {
// sayHello(10)//error
sayHello("lee",
20)
sayHello(no=10)
sayHello(name="kim",
no=10)
}
# Kotlin - if문
- 코틀린에서 if는 표현식(expression) 가능
fun main(args: Array<String>) {
val a
= 5
if (a < 10) println("$a
< 10")
//if
- else
if (a > 0 && a <= 10) {
println("0 < $a
<= 10")
} else if(a
> 10 && a <= 20){
println("10 < $a
<=20")
}else {
println("$a
> 20")
}
}
val result=if (a > 10)
"hello" else "world" // else 문이 꼭
필요함
# Kotlin - when (switch-case문 upgrade 버전)
- 표현식
- 문자가능, is 를 통한 타입 가능
- 여러 값 조건 표현 가능 ( , 이용)
- 범위 조건 표현 가능 ( .. 이용)
- 다양한 타입에 대한 조건 표현 가능
- else 가 꼭 있어야함
fun main(args: Array<String>) {
val a2=1
when (a2) {
1
-> println("a2 == 1")
2
-> println("a2 == 2")
in 3..10 -> println("3 <= a2 <= 10")
else ->
{
println("a2 is neither 1 nor 2.... 3~10도 아님!")
}
}
}
* 디컴파일해보면 모두 if-else if 구조로 되어있다.
# Kotlin - 반복문
- for 반복문
fun main(args: Array<String>) {
var sum:
Int=0
for(i in 1..10) {
sum +=
i
}
println(sum)
}
- while, do-while 반복문 가능
- break와 continue 사용 가능
• label 사용 가능 : 약간 goto 문 느낌? 그래서 잘 사용되지 않을 것
for(){
@label1
…..
continue @label1
}
# Kotlin - 연산자
- 코틀린은 연산자가 연산함수로 변경되어 처리하므로 연산자 오버로딩 가능
- 산술/대입/전개/복합/증감/논리/일치/비교/범위/nullcheck 등의 연산자
# Kotlin - 예외처리
- Java 와 같이 try-catch-finally 로 표현
- Checked exception 없음. (예외 강요하지 않음)
- 식으로 사용 가능. – 맨 마지막 값이 반환값.
fun readNumber(reader: BufferedReader) {
val number = try {
Integer.parseInt(reader.readLine())
} catch (e: NumberFormatException) {
null
}
println(number)
}
# 출처 : 모베란 백지훈 대표이사님
'Programming > Kotlin' 카테고리의 다른 글
[Kotlin]코틀린을 이용한 안드로이드 프로그래밍 실습 04 (0) | 2018.07.05 |
---|---|
[Kotlin]코틀린을 이용한 안드로이드 프로그래밍 실습 03 (0) | 2018.07.04 |
[Kotlin]코틀린을 이용한 안드로이드 프로그래밍 실습 02 (0) | 2018.07.03 |
[Kotlin] 코틀린을 이용한 안드로이드 프로그래밍 실습 01-1 (0) | 2018.07.02 |