Posted at
N高Day 4

未来の職人のための道具Nim!? YAMLとJSONの扱いを一例に (あんま怖くないNim④)

More than 1 year has passed since last update.


はじめに 

近い将来に、Scala+NimでIoTなサービスを作れたらいいなと考えている者です。

N高 Advent Calendar 2016初日『高校生にWeb上でプログラミングを教え始めたエンジニアがこの8ヶ月間で得た気づき』がなかなかいい話なのに、寄せられたコメントがアレ気味なのを見て、ちょっと気になったのではじめにコメント的なポエムを。...職人気質でC++erの方が「ついカッとなって」書いたであろうコメントをちら見するに、作家の橋本治(※)が昔々にいろんな意味を込めて書いていた「江戸時代、なめんなよ」的なエッセイが思い浮かんだ。

(※) こんな本を書いている人。

ということで、前半は、プログラミング学習について、江戸時代の職人修業を比喩にしつつ書いていく。後半で書きたいことは、N高では、職人さんたちの意見も取り入れたC言語につながる教育コース(課外部活動?)があってもいいんじゃないかな、ということの触りを。

とはいえ、C/C++の話を素人の私が書くと、荒ぶるC++職人の方々からいろいろ怒られかねないので、IoT技術者になるためのと素養といったあたりを、個人的な願いを込めて触りだけ書く。N高の教育言語、JS(Ecmascript)の次は、scala。で、N高 Advent Calendar2日目がなぜだかNimの話(やや深すぎるお話だったけど)。それに便乗して、JSONの処理などもさくっとかけてC言語にコンパイルされるNimなんかを教育言語にして、JSやscalaで書かれたアプリに、センサー情報をJSONをさくっと送れるよ、的なIoT教育なんかどうでしょうか、ということを思っていたり。

NimをN言語と呼べば、なんかN高っぽいしね。


「江戸時代、なめんなよ。」vs「何年も修行する職人はバカ」

産業革命的な要素を取り入れずに,当時世界最大となる人口100万人の新都市「江戸」を作り上げ、維持した江戸時代。戦がなくなったその治世は、いろんな職人気質文化が花開いた時期だったのだろう。当時の「職人」の仕事は、ダンドリの連続だ。例えば、冷蔵庫はない江戸時代に,花開いた寿司文化(参考)。酢で〆る、醤油で漬ける、火を通すなどの職人技の下処理があってこそ、おいしくグルメにいただける(はず)。食べ手がおいしく感じなかったら、「職人」の腕とダンドリが悪いから...

テクノロジー的支援が発達しなかった江戸時代においては、どの分野であれ一人前の職人になろうとするものは学ぶべきダンドリが多岐にわたったものと考えられる。さらに、寿司職人のダンドリと木工職人のダンドリはぜんぜん違うので、職業選択の自由はなくなりそう。(そもそも「士農商工」の身分制の時代の話だけど)。

伝統的な日本は良かった、江戸時代的な職人気質を現代に取り戻そう、って言うのは素敵な側面もあるけれど、江戸時代がオワコンになってから150年たった今、刺し身と各種の冷蔵・冷蔵庫でいい気がするし、客の好みの学習には機械学習がどんどん使われていくような時代。ITサービスにせよ寿司の提供にせよニコ動加工にせよ、職人はどんどんと高みを目指してほしいと個人的には思っている。職人、すげえ。ただ、「IT産業」としての事業性の話は時として別論となる。

このあたり、続きは以下におまかせするとして、本題に入っていこう。

ホリエモン「寿司職人が何年も修行するのはバカ」発言 数か月で独り立ちの寿司はうまいか?

個々人の話としてオチをつけておくと、コード書いてきちんと食べるようになれるならば、それでオーケー。N高からできるエンジニアが何人も出てくるといいな、といったところ。


プログラム技術の質と量

仕事につながるプログラミングの技術(スキル)には、質と量の両方の要素がある。

プログラミングスキルの質的な側面は、構造型プログラミングからはじまって、クロージャ、オブジェクト指向、ラムダ式、さらには、イベントループ、Null安全などなど、多くのプログラム言語に実装されている機能の基礎となる概念と関わる。ここでは、「頭」を使って理解することが求められる。他方は、スキルの量的な側面は、気に入ったプログラム言語でプログラムをどんどん書いて、この言語ではこう書くといイディオムを「手」になじませること。

両者には一定の関連があって、仕事で選ばれた言語がjavascriptならば、クロージャやイベントループを理解し、ブラウザやnodeでさくっと書く量的スキルが期待されるだろうし、選ばれた言語がscalaならば、オブジェクト指向、ラムダ式を活用した関数型のアプローチで、さくっと書く量的スキルが求められるだろう。もちろん、さくっと書いたものがbuggy(誤りだらけ)であってはいけない。書いたプログラムに誤りを混入させることを避けるには、正しい理解にしたがって技術を使いこなす質的スキルが期待される。

両方を高い水準で両立するのはなかなか困難で、私なんかも全然低い水準なのだけれども、それなりに楽しめる仕事は見つかったりして、それでスキルの質とスキルの量がちょっとアップする。スキルをきちんと身につけるためには、学習しやすい言語と実用性の高い言語をそれなりにバランス良く学ぶのが良いのではと思う。以下、学習しがいのある新言語Nimのさわりを少し紹介(というか、こちらが本題のつもりだったんだけど、前段が長くなりすぎたので、またの機会に。)


Cにコンパイルされるプログラム言語Nim

Pythonテイストな文法でC言語などにコンパイルされるNimってどんなもの、という話は、

N高カレンダー2日に力作を書いてくださった方のNimの簡単な紹介あたりからはじめてほしい。

あと、出版間近の「Nim in Action」に掲載されている図を引用しておこう。

nim-py.PNG

Nimは、Cで書かれたソフトウェア資産との相性が良い。開発がはじまってから10年ほど経っており、コンパイラも安定している(と感じる)。ただ、まだバージョン1に達していないしマイナーすぎるので、仕事で使うにしても2、3年先くらいかなというくらいのステータス。とはいえ、クロスコンパイルとか最適化とかに各種プラットフォーム向けのCコンパイラ(特に、gcc/clang)が使えるので、小さく始めてしまう手もありそう。

広く普及するかどうかはさておき、型安全等にモダンな工夫が取り入れられているNim,Pascalに変わる教育言語としてありなのではないかと思っている。少し気になった方は、C言語未経験者でもできる、という意味で書いている、普通のWindowsユーザー向けNimエントリー(これとか)もチラ見してほしい。


IoT時代に活きそうなNim(JSON/YAMLを扱う例)

はじめに書いたように、web上のコースであるため、高専などの差別化を意識してか、N高ではC言語のコースが用意されていない。現状のC言語エンジニアの多くが、チームプレーが求められる組込機器業界などで働いているためだろうか。あるいは、C系言語を使っているゲーム業界の企業とのコラボコースをいずれ用意するのだろうか。

いずれにせよ、自動運転機能などを持つスマートカーが大きな話題となる時代、N高の生徒さんが組込やIoTにつながるスキルに触れておくのは悪くないのではなかろうか。

ただ、CやC++で書いた組込機器をインターネットにつなぐ敷居は低くない。機器のメモリを自由に操作できるC/C++は、高い機能性と実用性を持つ、作りのちょっした甘さが、即セキュリティ問題(ハッキング)につながってしまう側面も持つ。人の生死に関わるような領域では、C/C++職人が半人前であることは許容されない。

ということで、近時の言語は危険なセキュリティホールを作らないよう、安全性についてのさまざまな工夫が行われている。新登場のNimもそうした言語の一つ。いわば、危険な記法を簡単に書けないようにするアプローチ。

Nimの安全性の話はいずれ(本格的に使うようになった後に)書くとして、ここからはNimの実用言語としての側面(見通しの良いコードが書きやすい)を少しだけ紹介しておこう。

お題は、Nim言語のみで書かれた(pure Nimな)ライブラリnimyamlでのJSONとYAMLの作成。

node使う人は当然学ぶだろうJSONは、オブジェクトのシリアライズ(永続化)の一般的な方法。YAMLはそんなJSONのスーパーセットでもあるシリアライズ方法(Ruby on RailsやPlay!などのwebフレームワークの設定の記述などに使われている)。Nimのnimyamlライブラリでは両者を気軽に扱える。

Nimのライブラリにしては珍しく、キレイめのドキュメントサイトもあって参考になる。

https://nimyaml.org/

インストール は、nimのパッケージツールnimbleで以下のようにタイプするだけ


nimble install yaml


のはずなんだけど、インストーラー経由でwindowsに入れたnimbleではうまく入らなかった。

こんなときは、pure nimであることを活かして、ソースコードごと持ってきてしまう。ソースコードも直接に見れるので一石二鳥。こちらのJSONパース実装と見比べてみるのもいいかもね。


git clone https://github.com/flyx/NimYAML


NimYAMLディレクトリに入ると、testディレクトリ以下にテストコードがあるので、それを参考に、以下のように書いて見る。


import "../yaml"

import streams
#Person型を定義
type Person = object
name : string
age : int32

#Personオブジェクトを生成
var personList = newSeq[Person]()
personList.add(Person(name: "木村カエラ", age: 31))
personList.add(Person(name: "キムニイ", age:50))
personList.add(Person(name: "木村カレハ", age:45))
personList.add(Person(name: "木村ヨーダ", age:1677000))

#YAML形式でファイルに書き出す
let sy = newFileStream("out.yaml", fmWrite)
dump(personList, sy)
sy.close()

#YAML形式でファイルに読み込む
let sj = newFileStream("out.json", fmWrite)
dump(personList, sj,
options = defineOptions(style = psJson))
 #オプションでJSONでのシリアライズを指定
sj.close()

varとletの使い分けは、swiftやscalaと同様。C言語に比べるとだいぶ簡潔な記法となる。

※冒頭の「import "../yaml"」は、Nimソースコードから直接にライブラリを取り込む時のソースコードの指定方法。

yaml.nimの方は以下のようで、ライブラリ本体とのつなぎ役か。


yaml.nim

import yaml.dom, yaml.hints, yaml.parser, yaml.presenter,

yaml.serialization, yaml.stream, yaml.taglib, yaml.tojson
export yaml.dom, yaml.hints, yaml.parser, yaml.presenter,
yaml.serialization, yaml.stream, yaml.taglib, yaml.tojson

nim c コマンドコンパイルしてできあがったexeファイルを実行すると、以下の2つのファイルが得られる。


out.yaml

- 

name: 木村カエラ
age: 31
-
name: キムニイ
age: 50
-
name: 木村カレハ
age: 45
-
name: 木村ヨーダ
age: 1677000


out.json

[

{
"name": "木村カエラ",
"age": 31
},
{
"name": "キムニイ",
"age": 50
},
{
"name": "木村カレハ",
"age": 45
},
{
"name": "木村ヨーダ",
"age": 1677000
}
]

簡潔なYAMLと広く使われいてるJSONが統一的に扱えるのがなかなか便利なライブラリ。興味を持った方は、YAML/JSONからの読み込み(デシリアライズ)や、サーバーとの通信にチャレンジしてほしい。あとC++erの方々は批判的な目をもってNimが吐き出すC/C++のコードを見ていただきたい。


未来の職人のための道具Nim!?

少し長い目で見ると,かけた学習コストで得られる生産性は大事なパタメーターであるはず。C系言語に代替する言語へのニーズは、iOS開発でのobjective-c -> swift登場 -> ... -> Swift3.0 ->...といった変遷が、もっとも有名な例だろう。グーグルのGoもその一例(さらにDやrustが,いったあたりは職人の方々にお任せてしておく。)。

まだまだマイナーな言語のNimではあるけれど、nimyamlの作者はじめ、職人的にライブラリを書いている方も登場している。近い将来に、Nimが,教育用言語やプロのエンジニアためのの道具になっていくといいなという期待でこのエントリーを終えておく。

尻切れトンボなエントリーになったので、続きは、Nim Advent Calendar 2016に、clangとNimをお題にきちんと書きたいなと思う!