【Java】計算のしくみと演算子と型変換

# Javaの計算のしくみ
```
5 + 4
```

これは説明なくそのままです。
5 と 4 を足し算して 9 の答えをJavaが出してくれます。

では

```
5 + 4 - 3
```

の場合はJavaはどのように計算をするか？:thinking: というと、まず

5 と 4 を足し算して 9 を求めます。
そのあと 9 - 3 で引き算をして 6 を求めます。

ちなみにこの 5 と 4 と 3 を**オペランド**といい
+ と - を**演算子**といいます。

Javaが式に従って計算処理することを**評価**といいます。
オペランドと演算子を使ってだした計算結果を**化ける**といいます。
さっきの式の 5 + 4 - 3 でいうならば、まず 5 + 4 を評価して 9 に化ける。
そのあと 9 - 3 を評価して 6 に化ける。
という感じです:smile:

```
5 + 4 * 3
```

掛け算が混ざった計算式。
学校で習った順番と同じです:smile:

まず 4 ✕ 3 で評価して 12 に化けます。
そして 5 + 12 を評価して 17 に化けます。

```
(5 + 4) * 3
```

この場合も学校で習った順番と同じです:smile:
まず（）の中身を計算します。
(5 + 4) を評価して 9 に化けます。
そのあと 9 ✕ 3 を評価して 27 に化けます。

```.
5 / 4
```

この場合はどうなるでしょうか？:thinking: 
普通に計算すれば答えは 1.25 です。
しか〜し、1.25 では出てきません。
正解は 1 です。

理由は簡単です:smile:
整数同士の計算だからです。
小数点以下はバッサリと切り捨てられます。

なので、小数点以下も表示したいときは

5.0 / 4 もしくは 5 / 4.0 もしくは 5.0 / 4.0

と、どちらか、もしくは両方とも小数にしてあげれば 1.25 と表示されます:smile:

# 代入演算子
:sunny: 右側のオペランドの内容を左側のオペランドの変数に代入する

なんだか小難しく説明してしまいましたが[変数](https://qiita.com/mikimikiman/items/dee9b6dd46a2ca03741e)を思い出していただければ容易いかと。

```例.java
number = 10;
```

こやつのことです:sweat_smile: 
右オペランドは、ここでいう 10 のこと。
左オペランドは、ここでいう number のこと。
つまり 10 を number に代入してくださいってことです:smile:


代入演算子は = の他に別の演算子と組み合わせたものがあります。

例
a += 5(a = a + 5 の意味)
a -= 5(a = a - 5 の意味)

など。
意味としては a に 5 を足して a に代入してください。
a に 5 を引いて a に代入してください。
となります。

もしも a に初期値として 6 が入っていたとしたら
6 + 5 を先に計算して 11 となり 11 が a に代入されます。
引き算のほうであれば、6 - 5 を先に計算して 1 となり 1 が a に代入されます。

# インクリメント演算子とデクリメント演算子
代入演算子で a += 5(a = a + 5 の意味) と説明しましたが
1 だけを増やしたい場合は他にも記述方法があります。

```インクリメント演算子.
a++;
```

a += 1 もしくは a = a + 1 と同じ意味です:smile:
この変数の値を1だけ増やすのをインクリメント演算子といいます。

```デクリメント演算子.
a--;
```

インクリメント演算子とは反対に
変数の値を1だけ減らすのをデクリメント演算子といいます。

基本的にインクリメント・デクリメント演算子は他の演算子とは一緒に使用しません。
一緒に使用してしまうと微妙に計算違いが発生してしまいます。
そのためよっぽどの事情がないかぎり、単独で使用したほうがベターです。
（a++ * 50 など他の演算子と一緒にしない。使うときは a++; のみ）

# 型変換

```.
5 / 4
```

この計算のときに小数点の計算まで表示したいときは

5.0 / 4 もしくは 5 / 4.0

と記入するとお伝えしたかと思います。
これも型変換と呼ばれるものになります。

この型変換というのはいったいなんだ？？:thinking: 
ってことなんですが、**型変換というのはデータ型（intとかdoubleなど）を別のデータ型に変換することです。**

なので 5.0 / 4 と記入してもパソコンくんが勝手に

あー、はいはい。
5.0 / 4.0 を求めたらいいわけねー。

と自動的に解釈してくれて答えを 1.25 と表示してくれるのです。
小数 / 整数 だったのを 小数 / 小数 に型を自動変換してくれてるというわけです。

## 整数 → 整数 への型変換

じゃあなんでもかんでも自動変換してくれるのか？:thinking: というと、そういうわけではないです。

|型名| 格納可能な整数の範囲	 |
|---|----------------|
|byte| -128〜127 の整数 |
|short| -32768〜32767 の整数	 |
|int|-2147483648〜2147483647 の整数|
|long|-9223372036854775808〜9223372036854775807 の整数|

上の図を見てもらうと
byte なら -128〜127 の整数
short なら -32768〜32767 の整数
となっています。

少し想像していただきたいのですが・・・

byte は格納できる整数の範囲が short にくらべて少ないので小さな箱とします。
short は格納できる整数の範囲が byte よりは多いので大きな箱とします。

小さな箱は大きな箱へ格納することができます。
しかし大きな箱は小さな箱へ格納することができません。
はみ出るか箱自体が壊れちゃいます。

これと一緒で型変換も小さなものから大きなものへは型変換できます。
しかし大きなものから小さなものへは例外を除いて原則、型変換できません。

## 整数 → 小数
5.0 / 4 のときに説明したとおり小数であらわすことができるので型変換可能です。
整数から float へ型変換できるし、整数から double へ型変換可能です。 

## 小数 → 小数
整数と一緒で箱の大きさが関係します。
float よりも double のほうが格納できる箱が大きいため
float → double へは型変換可能ですが
double → float へは型変換できないです。

## 小数 → 整数
何度もでてきて申し訳ないのですが、5.0 / 4 としたときに計算した答えは 1.25 になったかと思います。
つまり 小数 → 整数 には型変換ができません。

## 型変換まとめ
ここで箱の大きさベスト６を発表したいと思います:tada::raised_hands:
１位の箱が一番大きく、６位の箱が一番小さいです。

ジャジャン！

|順位|:gift:箱の大きさベスト6:gift:|
|---|-------------|
|1位|double|
|2位|float|
|3位|long|
|4位|int|
|5位|short|
|6位|byte|

これで少し想像つきやすくなったでしょうか？

６位の byte くんは一番箱が小さいので自分よりも大きな箱の 1位から５位 の型へ型変更可能です。
3位の long くんは 自分より小さい箱の 4位から６位 の箱へは型変更できませんが、
自分より箱の大きい 1位と２位 の箱へは型変更可能です。
１位の double くんは一番大きな箱の持ち主なので型変更は不可能です。

今更ですが型変更の方法を記入しますね:sweat_smile:

```例.java
public class Main {
	public static void main(String[] args) {
		int number = 5;
		double decimal = number;
		System.out.println(decimal);
	}
}
```

3行目で整数 5 を変数 number に代入しました。
型が int なので整数です。

４行目で変数 number を変数 decimal に代入しました。
型が double なので小数に変換されます。

```コンソール.
5.0
```

## 整数の変数同士の割り算を小数であらわす

```例.java
public class Main {
    public static void main(String[] args) {
        int number1 = 5;
        int number2 = 2;
        System.out.println(number1 / number2);
    }
}
```

上記のように整数の変数同士の割り算では出てくる結果が整数の 2 です。
ちゃんと小数まであらわしたい場合は・・・？:thinking: 

int 型を double 型に変更するというのも間違いではないのですが
そのたびに変更するというのも面倒です。

```例.java
System.out.println((double)number1 / number2);
```

計算式の変数の前に (double) を追加してあげればＯＫです:smile:
ちなみに number2 のまえに (double) をつけても問題ないです:smile:

**このように手動で強制的に型変換することからキャストと呼びます。**

## 大きな型 → 小さな型へ
大きなものから小さなものへは例外を除いて原則、型変換できません。とお伝えしました。
厳密に言えばできてしまうのです。これが:sweat_smile: 
"例外を除いて" の部分ですね:sweat_smile: 
こちらも**強制的に型変換するのでキャストといいます。**

箱の大きさベスト6 で第４位の int くん。
一番大きな箱をもつ double くんがむりやり int へ型変換しようとしています。

```
（変換先の型名） 式
```

で強制的に型変換できます。

```例.java
public class Main {
	public static void main(String[] args) {
		int number = (int)5.8;
		System.out.println(number);
	}
}
```

```コンソール.
5
```

小数 5.8 が整数の 5 になりました:smile:

大きい型から小さい型へ変更できるのなら別に気にしなくていいじゃん:thinking: 
と思ってしまいますが、これあまり推奨しません。。

というのも、小さな型に無理矢理データを押し込んでいるのデータの一部を失ったり、欠損した部分が原因で不具合につながることもあります。
そのため最終手段としてどうしても使わなければいけないというような理由でもない限り使わないほうがいいです:sweat_smile: