Elm 0.19で、Elmに速攻入門。

# バージョン1.0が見えてきたElmが良さげなのでお試し。
 バージョン0.19がリリースされ、その先にバージョン1.0が見えてきたというElm。
『[今勢いのある言語 Elm](https://qiita.com/ababup1192/items/c48df0495728f89f756a)』という勢いあるエントリーに乗っかって、入門してみた次第。インストールやコマンド体系などが今までのバージョンと違うようだったので、備忘録をここに記す。

##入門者のスペック
Haskellは以前に2冊くらい本を読んだ程度。Scalaはベターjavaとして実案件で活用。普段はPythonを使う。趣味は、同じくバージョン1.0出るか出たよが話題となる、NimとJulia。以前、フロントエンドも自前で書いた時に辛かったので、Immutableな言語で仮想DOMを操作してフロントエンドを完結できるならいいねと、Elmに期待（加えて、Mutableな処理をガリガリ書く必要があるならば、[Nimでwebassembly](https://qiita.com/Nimimal/items/0499575bc64e49c9f998)といきたいところ）。
##時短に役立つ『Elm入門ハンズオン』
https://gitpitch.com/ababup1192/elm-handson1/master?grs=github&t=sky

カーソルキーを上下左右に動かしながらElm入門ができる素晴らしい資料。
本ハンズオンは、Elm0.18対応と思われるが、Elm0.19でもほぼほぼ動いた。
ブラウザ上の動作に特化したElmは、HaskellやScalaやNimに比べるとシンプルな言語仕様と思われ、言語仕様を軽く眺めDOMをいじってみるまでは、１時間ほどで行えた。

#Elm 0.19に速攻入門記
## （当座の）インストール方法
リリースされたばかりのElm0.19は、npm経由のインストールが推奨されていない（できない場合がある）模様。そのため、以下の指示に従う。

https://guide.elm-lang.org/install.html

いずれのプラットホームも簡単に入りそう。
Linux(debian等)の場合:

Elm 0.19 just came out, so the `npm` installer is not ready yet. In the meantime, you can download it manually like this:

```bash
wget "https://github.com/elm/compiler/releases/download/0.19.0/binaries-for-linux.tar.gz"
tar xzf binaries-for-linux.tar.gz
sudo mv elm /usr/local/bin/
```
ということで、elmのお試しだけならnode.js./npmは必要ない(mvにsudoが必要なのは、Windows 10上のWSL debianなどの場合)。

## まずは、elm init

elm0.19では、作業ディレクトリにて、
> elm init

とするのがお作法な模様。Scalaでいうsbtのようなものか。

```.sh
kmry:/mnt/c/dev/elm1$ elm init
Hello! Elm projects always start with an elm.json file. I can create them!

Now you may be wondering, what will be in this file? How do I add Elm files to
my project? How do I see it in the browser? How will my code grow? Do I need
more directories? What about tests? Etc.

Check out <https://elm-lang.org/0.19.0/init> for all the answers!

Knowing all that, would you like me to create an elm.json file now? [Y/n]: Y
Okay, I created it. Now read that link!

kmry:/mnt/c/dev/elm1$ tree .
.
├── elm.json
├── elm-stuff
│   └── 0.19.0
│       ├── Elm_Repl.elmi
│       ├── Elm_Repl.elmo
│       └── summary.dat
└── src

kmry:/mnt/c/dev/elm1$ cat elm.json
{
    "type": "application",
    "source-directories": [
        "src"
    ],
    "elm-version": "0.19.0",
    "dependencies": {
        "direct": {
            "elm/browser": "1.0.0",
            "elm/core": "1.0.0",
            "elm/html": "1.0.0"
        },
        "indirect": {
            "elm/json": "1.0.0",
            "elm/time": "1.0.0",
            "elm/url": "1.0.0",
            "elm/virtual-dom": "1.0.0"
        }
    },
    "test-dependencies": {
        "direct": {},
        "indirect": {}
    }
}


```

...だいたい雰囲気はわかるだろう。elm.jsonに必要なパッケージを記していくものらしい。

##次いで、elm reactor

開発用のwebサーバー（reactor）を立ち上げながら、エディタでelmコードを書いていくというのが流儀らしい。エラーが出た場合もブラウザ上で確認する。

```
kmry:/mnt/c/dev/elm1$ elm reactor
Go to <http://localhost:8000> to see your project dashboard.
```

http://localhost:8000にアクセスしてみる:

![localhost.PNG](https://qiita-image-store.s3.amazonaws.com/0/16455/a25bc452-8983-f38d-7440-d36d8f1cb29b.png)


ということで、src配下にコードを書いていくらしい(自分の場合、VS-codeにelm拡張を入れた。)。
hello worldも、仮想DOM経由で行うのが流儀だろう。
helloとworldを宣言し、mainでつなげる:

```hello.elm
import Html exposing (..) --(h1, div, p, text)

hello =  h1 [] [text "hello"]
world =  p [] [text "world."]

main =
  div [] [ hello , world]
```

import Html exposing (..)することで、h1, div, pなどの仮想DOM要素一式と、何もタグで囲まれていない文字列Html a を作るtextとが使用可能となる。

実行結果:
![hello.PNG](https://qiita-image-store.s3.amazonaws.com/0/16455/38e87c49-a44b-447f-d7c9-6b7a31c9dbd3.png)

次いで、関数型言語らしく（？）、関数を使ってみよう。

```nobi1.elm
import Html exposing (..)

-- 識別名称をエイリアス宣言
type alias Name = String
type alias Age = Int
type alias Person = { name : Name, age : Age }

-- 代入用変数（≒オブジェクトの生成）
takeshi = { name = "剛田武", age = "10" }
nobi = { name = "野比のび太", age = "9" }

--表示用DOMの生成

get_text x s = text (x ++ s)
name_age x =
    div [] [
        h1 [] [get_text x.name  ":"] , 
        h2 [] [get_text x.age  "歳"] ,
        hr [] []
    ]

--mainを介し、仮想DOMを描画
main =
    div [] [
        name_age(takeshi) , 
        name_age(nobi)
    ]
```

実行結果:

![nobi.PNG](https://qiita-image-store.s3.amazonaws.com/0/16455/0e9c9a40-63f8-5f00-541a-4c22bc36d23e.png)

『hr [] []』ってなんのことだろうとか若干気になるが、ともあれ，変数・関数を駆使し、ブラウザのDOMに反映できていることはわかるだろう。

ここから先は、ラジオボタンやプルダウンなどで、スネ夫やしずかちゃんを登場させるところは略する。ていうか、ボタンを用意するからには、サーバ側とデータをやり取りしたいよねと思ったあたりで、１時間経過したので、そのあたりの入門は今後の課題とする。

#おまけ（Haskellになじみがない方向け）:elm repl

node.jsが入っている環境では、elm replとタイプすることで、nodejsを活用したREPL環境でHaskell風なElmの関数型言語テイストな記述をお試しできる。
Haskell風な体系では、f(x)はf x とも記せる:

```.elm
> f x = x^2
<function> : number -> number
> f 5
25 : number
> f (3)
9 : number

> g (x) = x*2
<function> : number -> number
> g 4
8 : number
> g (2)
4 : number
```

このかっこが省略できる記法に慣れておくと、関数渡しの場合などに可読性が向上すると思っている。
例えば、

```.elm
> f (g 2)
16 : number
```
の場合、カッコ内のg 2を先に評価し、f(結果)を得ると読める。
ElmをHakellライクな言語として入門する場合には、REPLを使うのが良さそう。

```.elm
> h x = if x > 4 then True else False
<function> : number -> Bool
> h (5)
True : Bool
> h (f 5)
True : Bool
> h (f 1)
False : Bool
```

#0.19で、ちょっと困ったこと。
整数型を文字列型に変換する、toStringが使えなかった。モジュール体系が変わったからなのかな？？？

まぁ、Elmで仮想DOMな雰囲気は体験できたから良しとする。