※ この記事はZigを初めて触った人が書いた記事です。Zigを初めて触った人はこんな感想を持つんだ、という参考として受け取っていただければ幸いです。
めっちゃ強いOBに「次に流行る言語はなんですかね?」って聞いたらZigって言われたので、この前書いた電卓自作の記事をZigで走ります。
弊環境ではパッケージマネージャにyayを使っているので、インストールはyay -S zig
だけで済みます。
1 Introducing Zig – Introduction to Zig を読んだところ、zig init
, zig build-exe src/main.zig
をすると実行バイナリが出来上がるそうです。makefileとか書く必要がないのは良いですね。最近の言語は大抵そうですが。
zig build
をすると、カレントディレクトリにあるbuild.zig
をもとにいい感じにビルドしてくれるみたいです。
見た感じroot.zig
にライブラリ的な関数をおいて、main.zig
にmain関数を置く感じなのでしょうか?それぞれに対するテストは、コードと同じファイルに置く思想みたいです。コードとテストが近いのはわかりやすくて良さそうです。
ステップ2
数の入力方法がよく分からなかったので、とりあえずステップ2から始めます。書いたコードは以下のような感じになります。
const std = @import("std");
なんかはCommonJSみを感じます。const stdout = std.io.getStdOut().writer();
という関数を関数の外で呼び出せるのは不思議な感じがします。readUntilDelimiterOrEof
の使い方を理解するまで時間がかかりました。- バッファ側をいじるんじゃなくて戻り値を使うんですね・・・。
try
とorelse
でエラー処理をするのは結構好きです。Go言語のif err != nil { ... }
より好きです。- (ここで実装したものは入力文字列を全部出力していて、本来のステップ2とは少し異なります。)
ステップ4
- 細かい実装はさっさと飛ばしてステップ4です。
- せっかくなのでテストも含めて全部のコードを載せておきます。
- テストも書きましたが、すべてのファイルのテストを一つのコマンドで纏めて実行する方法が分からなくて調べました。テスト|Zigについてのメモ この記事によると、
zig build test
で良いとのことです。 - 電卓自作では入力された文字列をグローバル変数に置いていたのですが、今回のコードではresultがconstなのが気持ちよかったので、各関数にconstで渡していく形にしてみました。
- 配列の処理について
- for文で要素を取り出せる構文があるのは良さげに感じました。が、今回のコードでは地道にwhileで処理しています。
- 配列の長さを配列と一緒に扱えるのは良さげに感じました。テストビルドでは範囲外参照のエラーも出してくれるのはありがたいです。
ステップ9
- 足し算と引き算を実装してみました。
- 差分はステップ9 · soukouki/zig-calc@53c8f4e · GitHubから確認できます。
ステップ13
- 掛け算と割り算を実装してみました。
- 割り算をする際に、
i32
については割り算ができない、というエラーメッセージが出ました。- 具体的には、
result /= next
をするとerror: division with 'i32' and 'i32': signed integers must use @divTrunc, @divFloor, or @divExact
というエラーが出ました。 - Zig の文書読んで所感を記す 2 ZIG - Qiita にどうしてこのエラーが出るのかが解説されています。
- 具体的には、
- 差分はステップ13 · soukouki/zig-calc@74813ee · GitHubから確認できます。
ステップ15
- 括弧を実装してみました。
- 差分はステップ15 · soukouki/zig-calc@0c0e3dd · GitHubから確認できます。
全体を通しての感想
今回触った範囲はかなりさわりの部分だけなので、Zig言語全体に対する感想ではありません。特に構造体やスレッド、C言語との相互運用などについては一切触っていません。
- C言語とGo言語の中間みたいな味をしつつ、不便なところは積極的に改善しているように感じました。
- 標準入力を受け取るときにバッファを用意して〜、というところはC言語みを感じました。
- Go言語でよく書かされる
if err != nil
の代わりに、Error!
型とtry
の組み合わせがあるのは良いと感じました。
- 配列の範囲外参照について、範囲外アクセスをした瞬間にエラーを出すのは安全側に振っていてありがたいなと感じました。
- ただ、アクセス範囲を毎回判定する分のオーバーヘッドはどう考えているのかなと不思議に思っています。
- Zigにはビルドシステムが存在するのはありがたかったです。
- C言語ではMakefileと毎回戦っているのですが、それが楽になります。
- 強いて言えば、パッケージマネージャまで同封されていれば、他のモダンな言語のように簡単にライブラリを呼び出せて良いのにな、とは思います。