【Android】Kotlinで電卓作成 プログラム編





下記の記事
https://qiita.com/yanasep/items/503b378c439752f70880
を参考にしながら電卓を作成しました。

数字ボタン
初期値の0だったら、ボタンの数字を入れ、それ以外だったら、入力した値を追加して行きます。

```Kotlin:calcApp/app/src/main/java/com/example/calcapp/MainActivity.kt
        zero.setOnClickListener{
            if (calc_display.text == "0") calc_display.text = "0"
            else calc_display.text = "${calc_display.text}0"
            inputNum += "0"
        }
        one.setOnClickListener{
            if (calc_display.text == "0") calc_display.text = "1"
            else calc_display.text = "${calc_display.text}1"
            inputNum += "1"
        }

...

```

###演算子ボタン
addInput()でinputNum(文字型)をdoubleに変換して配列に格納。
演算子も演算子用の配列に格納。
inputNumは次の数値入力のため初期化します。

```Kotlin:calcApp/app/src/main/java/com/example/calcapp/MainActivity.kt
        plus.setOnClickListener{
            calc_display.text = "${calc_display.text}+"
            addInput(inputNum,'+')
            inputNum = ""
        }
        minus.setOnClickListener{
            calc_display.text = "${calc_display.text}-"
            addInput(inputNum,'-')
            inputNum = ""
        }
...
```

```Kotlin:calcApp/app/src/main/java/com/example/calcapp/MainActivity.kt
private fun addInput(inputNum:String, ope:Char){
        try {
            var num = inputNum.toDouble()
            numList.add(num)
            if (ope != '=') opeList.add(ope)
        }catch(e:Exception){
            calc_display.text = "Numeric Error"
        }
    }
```

=ボタンは、計算処理が入ります。


```Kotlin:calcApp/app/src/main/java/com/example/calcapp/MainActivity.kt
equel.setOnClickListener{
            calc_display.text = ""
            addInput(inputNum, '=')
            val result = calculation().toBigDecimal()
            calc_display.text = result.stripTrailingZeros().toPlainString()
            inputNum = ""
            numList.clear()
            opeList.clear()
        }
```

calculation()の戻り値は下記の理由によりdoubleからStringに変換した物を戻り値にして、その後にBigdecimal型に変換しています。
>https://www.ne.jp/asahi/hishidama/home/tech/java/math/bigdecimal.html
>BigDecimal自身は10進数の固定小数を扱えるのだが、doubleを使って初期化する場合、doubleは2進数の浮動小数なので、BigDecimalに変換する際に小数点以下の値が変わってしまうことがある。
その為、小数を扱いたい場合は、doubleを使わず、Stringで初期化する方がよい。

```Kotlin:calcApp/app/src/main/java/com/example/calcapp/MainActivity.kt
val result = calculation().toBigDecimal()
```

小数点第一位が0の時に整数として表示するため0削除と文字型に変換。
BigDecimal使用時にtoString()を呼ぶと指数表記になることがあるため、toPlainString()を使用。

```Kotlin:calcApp/app/src/main/java/com/example/calcapp/MainActivity.kt
calc_display.text = result.stripTrailingZeros().toPlainString()
```

calculation()
徐算と乗算を先に行います。
numListを計算した数に置き換え、次の数を削除します。

```
入力例
1*3/4-5+10

numList[2,3,4,5,10]
opeList[*,/,-,+]

while (i < opeList.size)の処理
1
2*3が行われ、3が消える。
合計の6が代入される。
numList[6,4,5,10]
opeList[/,-,+]
opeList.size=3
i=0
2
6/4が行われ1.5が代入される。
4は消える。
numList[1.5,5,10]
opeList[-,+]
opeList.size=2
i=0
3
-を負の数に変換。
opeListを+に変更。
numList[1.5,-5,10]
opeList[+,+]
opeList.size=2
i=1
4
+だったため特に何もしない。
numList[1.5,-5,10]
opeList[+,+]
opeList.size=2
i=2

for(i in numList)の処理
numList[1.5,-5,10]
の内容を全て足しています。
```

```Kotlin:calcApp/app/src/main/java/com/example/calcapp/MainActivity.kt

private fun calculation():String {
        var i = 0
        var result = 0.0
        while (i < opeList.size){
            if(opeList.get(i) == '/' || opeList.get(i) == '*'){
                if(opeList.get(i) == '*') result = numList.get(i) * numList.get(i+1)
                else result = numList.get(i) / numList.get(i+1)

                numList.set(i,result)           //計算に使った一つ目の数を計算結果に置き換え
                numList.removeAt(i+1)           //二つ目の数をリストから削除
                opeList.removeAt(i)             //使い終わった演算子をリストから削除
                i--                             //リストの次の要素が一つ手前に来たのでiを一つ戻す
            } else if (opeList.get(i) == '-') {
                opeList.set(i, '+')
                numList.set(i + 1, numList.get(i + 1) * -1) //引かれる数をマイナスにしてあとでまとめて足す
            }
            i++
        }

        result = 0.0
        for(i in numList){
            result += i
        }

        return result.toString()
    }

```


全コード
https://github.com/CoffCookie/calcApp/blob/master/app/src/main/java/com/example/calcapp/MainActivity.kt

デザイン編
https://qiita.com/clipbord/items/53b832066b1269dcc822