Javaの変数宣言・初期化・データ型（キャストとプロモーション）

###本記事の目的
Javaを勉強中で、勉強したことをアウトプットして知識の定着を図るために記事に起こしています。
学んだことを以下のように分けて記載していきます。

・[Javaの変数宣言・初期化・データ型（キャストとプロモーション）](https://qiita.com/drafts/3878a38d2ba6c1a0570d/)
・型変換
・変数のスコープ
・文字列の操作（準備中）
・配列の操作（準備中）
・演算子（準備中）
・条件分岐（準備中）
・繰り返し処理（準備中）
・クラスについて（準備中）
・抽象クラス（準備中）
・インターフェース（準備中）
・カプセル化（準備中）
・モジュールについて（準備中）

###変数定義
Javaで変数を定義するには、以下の2ステップが必要になります。
 1.変数に入れる値のデータ型を指定する
 2.変数名を決める

　　例：
　　　1. int（数値）型
　　　 `int number;`
　　　　intが数値を表すデータ型で、numberが変数名です。
　　　　上記の例ではint型の変数numberが定義されています。
　　　2. string（文字）型
　　　　`String text;`
　　　　Stringが文字列を表すデータ型で、頭文字を大文字にします。textが変数名です。
　　　　上記の例ではString型の変数textが定義されています。

　　　1、2同様に、文末にはセミコロンをつけます。

###変数の名づけルール
・先頭文字は、
アルファベット大文字／小文字、$、_等の記号

・大文字小文字は厳密に区別される。

・数字は2文字目以降使用可能。

・文字数（長さ）の制限はない。

・null,true,falseは使用不可。

・予約語は使用不可。
予約語とは、Java言語で既に使用されている名前の事。
例：if,while,switch など


###変数の初期化
下記の例のように、変数定義と同時に値を代入することを変数の初期化と呼びます。
　　　例：
　　　1. int（整数）型
　　　 `int number = 3;`
　　　　上記の例ではint型の変数numberが定義され、数値の3が代入されています。
　　　2. String（文字列）※ *Javaの基本型には、複数の文字を表す文字列型はありません。文字列型はStringというクラスとして提供されています。*
　　　　`String text = "文字";`
　　　　上記の例ではString型の変数textが定義され、文字列の「文字」が代入されています。

　　　　
###javaのデータ型
上記の説明で型が出てきましたが、型も値の種類によって細かく分けられます。
扱えるデータの範囲に応じてデータ型があります。データの範囲が大きいとそれだけメモリを消費します。扱うデータの量や、メモリの容量によって適切なデータ型を選ぶようにしましょう。

####整数型
| データ型       |  サイズ    |   値の範囲   | 
|:-----------------|:-----------------|:-----------------|
| byte             | 1byte |-128から127までの整数の値  |
| char           | 1byte | '\u0000' から'\uffff'までの整数の値。（これは、0から65535である）  | 
| short             | 1byte| -32768から32767の整数の値  |
| int               | 1byte| -2147483648 から2147483647まで整数の値。 |
| long             | 1byte| -9223372036854775808から9223372036854775807までの整数の値。 |

####浮動小数点型
| データ型     | サイズ |   値の範囲   |
|:-----------------|:-----------------|:-----------------|
| float          | 4byte |       32ビット単精度小数点       |
| double           |     8byte |  63ビット単精度小数点       |

####論理型
| データ型     | サイズ |   値の範囲   |
|:-----------------|:-----------------|:-----------------|
| boolean          | 1bit |  真（true）か偽（false）のどちらかの値。      |



####参照型
参照型にはクラス型、インターフェイス型、型変数、配列型の4つがあります。
クラス型とインターフェイス型のデータは、オブジェクトのある場所を示しており、配列型のデータは配列オブジェクトのある場所を示しています。
これまでのような基本型との違う点は、基本型がデータそのものを表しているのに対して、参照型はデータのある場所を示しているというものです。
わかりやすく言うと、基本型は家そのものを表しており、参照型は家の住所を表しています。

例：

```Main.java
class Main{
  public static void main(String args[]){
    int a[] = {1};
    int b[] = a;  //ここでbがaと同じ参照値を持つ
    System.out.println(a[0]);  //aとbは同じ出力結果になる
    System.out.println(b[0]);

    b[0] = 5;  //参照先の値が更新される

    System.out.println(a[0]);  //aとbは同じ出力結果になる
    System.out.println(b[0]);
  }
}
```

実行結果
↓

```
1
1
5
5
```

上記の例では、aとbは「int b[] = a;」というコードによって同じ参照先を見ています。5行目の「b[0] = 5;」というコードで参照先の値が変わるまでは、ともに「1」を参照していますが、参照先の値が「5」に更新されてからは「5」を参照しています。
####キャスト（型変換）
変数の型変換を行うことをキャストと言います。はじめはint型にしていた変数をlong型にしたり、その逆もできたりします。乗算等の計算時は、同じデータ型同士でないとできません。型の違うものを計算する時は、変換して同じ型にします。
Javaの型変換の方法として、自動での変換方法と手動での変換方法があります。
String型とint型を足すと、int型が自動でString型に変換されます。

例：

```test.java
System.out.printIn("りんごが" + "5" + "個あります");
```
→　"りんごが" + "5" + "個あります"と変換され、

```
りんごが5個あります。
```
と出力されます。

整数型のint型であまりの出る計算をした際でも、計算結果は数値型になります。
例：

```test.java
System.out.printIn(5/2);
```

↓

```
2
```
実際は2.5が正解ですが、2.5はdouble型なのでint型同士の計算では出せません。
5/2の計算結果を2.5としたい時は、

```Main.java
System.out.printIn(5.0/2);
```
とします。int型とdouble型の計算結果はdouble型になるためです（一方がdoubleであれば結果はdoubleになる）。このように、計算結果を浮動少数で表す場合には整数を少数で表します。

int型同士の計算で正確な値を出したいときキャストを行います。

```Main.java
int number1 = 13;
int number2 = 4;
System.out.printIn((double)number1/number2);
```

↓

```
3.25
```


また、**大きい型から小さい型へのキャストはデータの一部が失われる可能性があります。**
元の基本型のデータ範囲とキャスト後の基本型のデータ範囲に注意してください。

```Main.java
public class Main {
 
    public static void main(String[] args) {
        double doubleMax = Double.MAX_VALUE;
        int result = (int) doubleMax; //doubleの最大値をint型にキャストし、int型の変数resultに代入
        
        System.out.println(doubleMax);
        System.out.println(result);
    }

}

```

実行結果
↓

```
1.7976931348623157E308
2147483647

```

エラーにはなりませんが、double型の最大値がint型の最大値に置き換わってしまい、意図しない値になっています。

###プロモーション（型昇格）
型変換にはプロモーションというものもあります。
プロモーションとは、値の計算時に自動で広い型に直して計算する仕組みのことです。
例えばどちらかの方がlong型の数値の計算では、もう一つの値の型も自動でlong型に変換されます。

byte型の変数aと、long型の変数bを計算します。結果をbyte型の変数answerで受け取ろうとしてもエラーになります。

```Main.java
class Main{
  public static void main(String args[]){
      byte a = 10;
      long b = 20000;

      byte answer = a * b;
      System.out.println(answer);
  }
}
```
実行結果
↓

```
//Type mismatch: cannot convert from long to byte
```


正しい結果を得るには、結果を受け取る変数answerの型を、byteからlongにします。

```Main.java
class Main{
  public static void main(String args[]){
      byte a = 10;
      long b = 20000;

      long answer = a * b;
      System.out.println(answer);
  }
}
```

実行結果
↓

```
200000
```


どちらもlong型ではない場合はByte型、short型、char型の値はint型に変換されます。

また、どちらかがfloatで、もう一方がdoubleではない場合、もう一方の値はfloatに変換されます。

```Main.java
class Main{
  public static void main(String args[]){
      byte a = 10;
      float b = 0.83f;

      byte answer = a * b;
      System.out.println(answer);
  }
}
```

実行結果
↓


```
//Type mismatch: cannot convert from float to byte
```

```Main.java
class Main{
  public static void main(String args[]){
      byte a = 10;
      float b = 0.83f;

      float answer = a * b;
      System.out.println(answer);
  }
}
```

実行結果
↓

```
8.3
```

または、計算結果をbyteでキャストすればエラーにはなりませんが、その場合は小数点以下が省かれるので厳密な答えにはなりません。

```Main.java
class Main{
  public static void main(String args[]){
      byte a = 10;
      float b = 0.83f;

      byte answer = (byte)(a * b);
      System.out.println(answer);
  }
}
```

実行結果
↓

```
8
```

もしプロモーションをせずにchar型やbyte型のまま計算すると、桁溢れで正しい答えになりません。
また、byte同士の計算もキャストしなければエラーになります。

```Main.java
class Main{
  public static void main(String args[]){
      byte a = 1;
      byte b = 2;

      byte answer = a * b;
      System.out.println(answer);
  }
}
```
実行結果
↓

```
//Type mismatch: cannot convert from int to byte Java

```
正しい結果を得るには、結果を受け取る変数answerの型を、byteからintにします。

```Main.java
class Main{
  public static void main(String args[]){
      byte a = 1;
      byte b = 2;

      int answer = a * b;
      System.out.println(answer);
  }
}
```
実行結果
↓

```
 2
```

または、byteで結果を受け取りたい場合は、計算結果をキャストしてbyteにします。

```Main.java
class Main{
  public static void main(String args[]){
      byte a = 1;
      byte b = 2;

      byte answer = (byte)(a * b);
      System.out.println(answer);
  }
}
```
実行結果
↓

```
2
```

###おわりに
このようにjavaでは型に気を付けないと思わぬところでエラーが発生するので気を付けましょう。