はじめてのKotlin:Kotlinのクラスの特徴をまとめてみた

# Kotlinクラスの特徴
　Kotlinのクラスには、以下のような特徴があります。思いつくままに列挙してみます。

- **new** キーワードなしでインスタンス化することができます。
    - **new** キーワードを付けてインスタンス化するとエラーになります。
- 構成要素はプロパティとメソッド(関数)のみです。
- プロパティ
    - デフォルト公開属性は **public** です。
    - **lateinit** キーワードを付加すると、後から初期化可能となります。この場合には、 **mutable** である必要があります。すなわち可変変数キーワード **var** で宣言する必要があります。
    - **lazy** キーワードを付加しても後から初期化可能です。この場合には**immutable** である必要があります。すなわち不変変数キーワード **val** で宣言する必要があります。
- クラス内の関数
    - クラス外関数とまったく同じ方法で定義します。
    - **fun** キーワードを付けて定義します。
    - 関数はメソッドと呼ばれることもあります。
- クラスとメソッドの継承可能性はデフォルトで **final** です。すなわち継承を許しません。
    - 継承させたい場合には明示的に **open** キーワードを付加します。
- クラス内に内部クラスであるインナークラスを定義できます。
    - インナークラスに明示的に **inner** キーワードをつけて定義すると、定義したクラス内のメンバーにアクセスすることができます。
- **init** キーワード付きのコードブロックはコンストラクタの定義となります。すなわち、インスタンス時に実行されます。
- 同一ファイル内に複数のクラスを含めることができます。

## 遅延初期化
　後から初期化する遅延初期化には、**lateinit** キーワードによるものと **lazy** キーワードによるものがあります。

　**lateinit** キーワードの場合には、 **mutable** ですので、可変変数キーワード **var** で宣言する必要があります。すなわち、初期化した後から変更することができます。

 **lazy** キーワードの場合には、 **immutable** ですので、不変変数キーワード **val** で宣言する必要があります。すなわち、初期化した後に変更することはできません。

```kotlin:遅延初期化するコード例
class LateinitAndLazy {
  lateinit var lateinitString: String
  
  val lazyString: String by lazy {
    val valueOfString = "This train consists 12 cars."
    valueOfString
  }
  
  fun lateinitStringLength() {
    lateinitString = 
      "Boardingn locations are indicated by white circles and No.1 through 7."
  
    val length = lateinitString.length
    println("Length of 'lateinitString' is $length" )
  
    lateinitString = "We are soon making brief stop at Bentencho."
  }
  
  fun lazyStringLength() {
    val length = lazyString.length
    println("Length of 'lazyString' is $length" )
  }
}

fun main( args: Array<String> ) {
  LateinitAndLazy().lateinitStringLength()
  LateinitAndLazy().lazyStringLength()
}
```
```text:遅延初期化するコード例の実行結果
Length of 'lateinitString' is 68
Length of 'lazyString' is 28
```
## クラスの継承
　クラスはデフォルト、つまり何も指定しないで宣言すると **final** クラスとなり、継承を許しません。
　**open** キーワードを明示的に付加して定義することで、定義されたクラスは継承を許します。

```kotlin:クラスの継承のコード例
open class Employee( name: String, age: Int ) {
  val name = name
  val age  = age
}

class Company: Employee( "Jhonson", 58 )
 
fun main(args: Array<String>) {
  println(
    "Name is ${Company().name} and " +
    "Age is ${Company().age}."
  )
}
```
```text:クラスの継承のコード例の実行結果
Name is Jhonson and Age is 58.
```
```text:openキーワードをつけなかった時のコンパイルエラー
prog.kt:6:16: error: this type is final, so it cannot be inherited from
class Company: Employee( "Jhonson", 58 )
               ^
```

## インナークラスの定義
　インナークラスの定義で**inner** キーワードをつけない場合、インナークラスを含む外のクラスのメンバーにアクセスすると、コンパイルエラーとなります。

```kotlin:インナークラスのコード例
class Outer {
  private val outer: String = "Outerクラス"

  class Child {
    fun child() = "Childクラス"
    fun errorChild() = outer //コンパイルエラー
  }

  inner class Inner {
    fun innerFoo() = outer
  }
}

fun main(args: Array<String>) {
  println( Outer.Child().child() )
  println( Outer().Inner().innerFoo() )
}
```
```text:インナークラスのコード例の実行結果
Childクラス
Outerクラス
```

```text:コンパイルエラー
innerClass.kt:6:24: error: unresolved reference: outer
    fun errorChild() = outer //コンパイルエラー
                       ^
````
## インスタンス時の処理の定義
　クラスがインスタンス化されるときに実行される処理は明示的に **init** キーワードブロック内に記述します。

```kotlin:initキーワードを利用したコード例
class Baa {
  val baa: Float

  init {
    baa = 3.14f
  }

  fun dispBaa() { println( "baa is $baa!" ) }
}
 
fun main( args: Array<String> ) {
  Baa().dispBaa()
}
```
```text:initキーワードを利用したのコード例の実行結果
baa is 3.14!
```
---
#### **Visual Studio Code**が好き
 　どうもMarkdownのコードのソースコードハイライトけが好きになれないです。個人的に、Visual Studio Codeの背景色とソースコードハイライトがお気に入りなのです。
LateinitAndLazy.kt : Visual Stduio Code on Windows10 Pro
![LateinitAndLazy.PNG](https://qiita-image-store.s3.amazonaws.com/0/124810/64f7a156-040b-6520-3bfd-d3de7b53b09a.png)
Compile and Execute: Windows PowerShell on Windows10 Pro
![LateinitAndLazyCompileExecute.PNG](https://qiita-image-store.s3.amazonaws.com/0/124810/3dd8f522-12be-2fe1-3b7d-b257f10f47e2.png)
innerClass.kt : Visual Stduio Code on Windows10 Pro
![innerClass.PNG](https://qiita-image-store.s3.amazonaws.com/0/124810/e5e11229-a6f3-4059-ac2f-09c8a3d6fb55.png)
Compile and Execute: Windows PowerShell on Windows10 Pro
![innerClassCompileExecute.PNG](https://qiita-image-store.s3.amazonaws.com/0/124810/9727466c-ae9f-d121-4cab-9c4798db98a0.png)