// 멤버 프로퍼티(변수)와 생성자를 동시에 선언
class SimpleClass(val name: String, var address: String, var age: Int = 41)
kotlin 클래스의 기본생성자는 클래스명 바로 옆 “()” 구문이다. 기본 생성자의 매개변수 선언을 val name: String 하면 멤버 프로퍼티(변수)선언과 기본생성자 매개변수 선언을 동시에 한 것이다.
public class SimpleClass {
private String name;
private String address;
private Integer age
public SimpleClass(String name, String address, Integer age) {
this.name = name;
this.address = address
this.age = age
}
public String getName() {
return name;
}
public String getAddress() {
return address;
}
public Integer getAge() {
return age;
}
public void setName(String name) {
this.name = name;
}
public void setAddress(String address) {
this.address = address;
}
public void setAge(Integer age) {
this.age = age;
}
}
Kotlin 클래스 선언이 위 Java 코드와 동일하다.
// var name: String <= var/val 를 붙이면
// 생성자 매개변수 선언과 동시에 멤버 프로퍼티(변수)를 선언한 것과 같다
class BasicClass(var name: String, var address: String) {
// var name:String <= 한 것 과 같다
...
}
// name: String <= var/val 를 붙이지 않으면 생성자 매개변수만 선언 한 것 이다.
// 그래서 멤버 프로퍼티(변수)를 꼭 선언 해야한다.
class BasicClass(name: String, address: String) {
var name:String
var address:String
...
}
위 경우에는 반드시 기본생성자의 초기화 init블럭이 있어야 한다.
**class BasicClass(var name: String, var address: String)** 처럼 프로퍼티 선언과 생성자 매개변수 동시 선언 하지 않으면 아래 예제 처럼 멤버 프로퍼티 선언과 함께 init블럭을 통하여 멤버프로퍼티의 초기화도 해주어야 한다.
class BasicClass(name: String, address: String, age: Int) {
// 프로퍼티선언과 동시에 생성자 파라메터로 값 설정이 가능하며 초기화 구문 까지 포함 된 것이다.
var name: String = name
var address: String
var age: Int
init {
this.address = address
this.age = age
}
}
name 프로퍼티는 var name: String = name 선언과 동시에 초기화 구문 까지 함께 기술 하였기 때문에 init 블럭에서 초기화 구분이 제외 되었다.
public class BasicClass {
private String name;
private String address;
private Integer age
public BasicClass(String name, String address, Intger age) {
this.name = name;
this.address = address;
this.age = age;
}
}
클래스 기본생성자의 초기화 init 블럭을 Java 코드로 표현하면 위와 같다.

class BasicClass(name: String, address: String, age: Int) {
var name: String
var address: String
get() = "$field 특별시"
set(address) {
field = "$address 특별시"
}
var age: Int
init {
this.name = name
this.address = address
this.age = age
}
}
val basicClass = BasicClass("김찬정", "서울", 10)
println(basicClass.address) // 서울 특별시 로 출력 됨
basicClass.address = "서울" // 서울 특별시 로 변경됨
기본적으로 getter/setter가 제공되지만 예제 처럼 override 한 것이다.
basicClass.getAddress(), basicClass.setAddress(“서울”) 처럼 사용해야 될 것 같지만 변수를 바로 다루는 듯 사용하며 실제로 getter/setter가 동작 한다.
// 아래 처럼 선언하면
class BasicClass(name:String) {
var name:String // public 생략됨
private var age: Int // 프로퍼티를 private로 선언하면
}
코틀린의 접근제한자는 기본적으로 멤버 프로퍼티(변수+getter+setter)에 대한접근 제한 자이다. public var name:String 은 name라는 변수는 private로 직접 접근이 불가능하며 기본으로 제공되는 getter/setter에 의해서 접근이 되는 것이고 getter/setter가 제공됨으로써 name프로퍼티는 public인 것 이다. 아래 예제를 보자 JAVA 코드로 변환 하면 실제로는 아래와 같다
public class BasicClass {
private String name;
private Integer age;
public String getName() {
return this.name;
}
public void setName(String name) {
this.name = name;
}
}
private var age: Int 프로퍼티를 private로 선언했기 때문에 Java 코드로 본다면 getter/setter가 제공 되지 않아 외부에서 접근 자체가 불가한 것이다.
class OverLoadingConstructor(name: String) {
// init 블럭 그리고 constructor에 초기화 구문이 둘다 들어가 있으므로 초기화 필요 없다.
var name: String
lateinit var address: String
// primitive type 프로퍼티는 사용 불가능 하기 때문에 0값으로 라도 초기화 해야한다.
var age: Int = 0
init {
this.name = name
}
constructor(name: String, address: String, age: Int) : this(name) {
this.name = name
this.address = address
this.age = age
}
}
// 다음과 같이 생성자가 제공된다.
val overLoadingConstructor = OverLoadingConstructor("김찬정")
val overLoadingConstructor2 = OverLoadingConstructor("김찬정", "서울", 20)
lateinit 이란 멤버프로퍼티의 값 초기화를 지연하는 키워드이며 다음과 같은 특징이 있다.
- var(mutable) 프로퍼티만 사용 가능
- non-null 프로퍼티만 사용 가능
- 커스텀 getter/setter가 없는 프로퍼티만 사용 가능
- primitive type 프로퍼티는 사용 불가능
- 클래스 생성자에서 사용 불가능
- 로컬 변수로 사용 불가능
class OverLoadingConstructorWithoutInit {
var name: String
var address: String = ""
var age: Int = 0
constructor(name: String) {
this.name = name
}
constructor(name: String, address: String, age: Int) {
this.name = name
this.address = address
this.age = age
}
}
// 다음과 같이 생성자가 제공된다.
val overLoadingConstructor = OverLoadingConstructor("김찬정")
val overLoadingConstructor2 = OverLoadingConstructor("김찬정", "서울", 20)
클래스 선언시 클래스명 옆에 기본생성자를 선언하지 않고 constructor를 선언한다. 그렇게 되면 init 블럭도 필요없어진다.