Qiita Teams that are logged in
You are not logged in to any team

Log in to Qiita Team
Community
OrganizationAdvent CalendarQiitadon (β)
Service
Qiita JobsQiita ZineQiita Blog
Help us understand the problem. What is going on with this article?

Kotlin入門:クラス

More than 1 year has passed since last update.

クラス

構文

class name(){
    definition
}

name:クラス名
definition:クラスの中身

入力例

class Person(){
      fun sayHello(){
          println("Hello")
      }
  }
  fun main() {
    val person = Person()
      person.sayHello()
  }

実行結果は以下の通りです。

Hello

①ではクラス名の後方に()があることに注意。
これはコンストラクターの引数を表すカッコです。

②ではインスタンス化していますが、new演算子は不要です。

アクセス修飾子

public:すべてのクラスからアクセス可能、既定のアクセス修飾子
protected:現在のクラスとそのサブクラスからのみアクセス可能
internal:同じモジュール内のクラスからのみアクセス可能
private:現在のクラスからのみアクセス可能

プロパティ

アクセサーを伴うプロパティの構文

構文

var name :type = init
getter
setter

name:プロパティ名
type:データ型
init:初期値
getter:ゲッター
setter:セッター

以下は入力例です。

class Person(){
    var name = "山田"
    var age = 20
        set(value){
         field = value
        }
    fun show(){
        println("名前は${name}です。年齢は${age}歳です。")
    }
}
fun main() {    
    val person = Person()
    person.age = 30
    person.show()
}

fieldはバッキングフィールドと言います。
バッキングフィールドとは、プロパティ値を格納するために
裏側で自動生成されるフィールドのことです。

実行結果は以下の通りです。

名前は山田です。年齢は30歳です。

以下の通り、settergetterは省略することもできます。

class Person(){
    var name = "山田"
    var age = 20
    fun show(){
        println("名前は${name}です。年齢は${age}歳です。")
    }
}
fun main() {    
    val person = Person()
    person.age = 30
    person.show()
}

プロパティ名がvar命令で宣言されているということに注意!

読み取り専用のプロパティ

val命令を使用すると読み取り専用のプロパティとすることができます。

class Person(){
    val name = "山田"
    var age = 20
    fun show(){
        println("名前は${name}です。年齢は${age}歳です。")
    }
}
fun main() {    
    val person = Person()
  person.name = "鈴木"
    person.show()
}

①でエラーが発生します。
getterの設定はできますが、setterの設定はできません。

private set

クラス外からのみ読み取り専用にしたい場合にprivate setterを使用します。

class Person(){
    val name = "山田"
    var age = 20
     private set
    fun show(){
        println("名前は${name}です。年齢は${age}歳です。")
    }
}
fun main() {    
    val person = Person()
  person.age = 25
    person.show()
}

①はアクセス権限のみを変更したい場合の書き方です。
setterには既定の実装が適用されます。

②でエラーが発生します。クラス内からではなく、クラス外からアクセスしようとしたためです。

アクセス修飾子を変更できるのはsetterのみです。

コンストラクター

コンストラクターには2種類あります。
プライマリコンストラクターセカンダリコンストラクターです。

まず1つ目のコンストラクターはプライマリコンストラクターとして扱い、
2つ目以降はセカンダリコンストラクターとして扱います。

プライマリコンストラクター

プライマリコンストラクターは、
クラスに1つだけ記述できるコンストラクターで、
classブロックの一部として表します。

class Person(name:String,age:Int){
    var name:String
    var age:Int
    init{
      this.name = name
        this.age = age
    }
    fun show(){
        println("名前は${this.name}です。年齢は${this.age}歳です。")
    }
}
fun main() {    
    val person = Person("鈴木",25)
    person.show()
}

①のような初期化コードを省略して以下のような書き方ができます。
以下でのポイントはクラスの引数にvar命令を用いていることです(valでも可)。

class Person(var name:String,var age:Int){
    fun show(){
        println("名前は${this.name}です。年齢は${this.age}歳です。")
    }
}
fun main() {    
    val person = Person("鈴木",25)
    person.show()
}

引数にvarまたはval命令を使用することで引数がプロパティ宣言とみなされます。

セカンダリコンストラクター

1つのクラスに2個以上のコンストラクターがある場合、
以降はセカンダリコンストラクターとして扱います。

class Person(var name:String, var age:Int){
  constructor(age:Int):this("鈴木",age){}
  constructor():this(15){}
    fun show(){
        println("名前は${this.name}です。年齢は${this.age}歳です。")
    }
}
fun main() {    
    val person = Person()
    person.show()
}

①1つ目のセカンダリコンストラクターで引数nameを省略しています。
②2つ目のセカンダリコンストラクターで引数nameageを省略しています。

セカンダリコンストラクターはconstructorブロックで定義します。
後方の:this()は他のコンストラクターを呼び出すための構文です。

プライマリコンストラクターが存在する場合、
セカンダリコンストラクターは最終的に必ずプライマリコンストラクターを呼び出さなければなりません。
上記のコードでコンストラクターが呼ばれる順番は
①→②→プライマリコンストラクター です。

asura
Why not register and get more from Qiita?
  1. We will deliver articles that match you
    By following users and tags, you can catch up information on technical fields that you are interested in as a whole
  2. you can read useful information later efficiently
    By "stocking" the articles you like, you can search right away