プログラミング Elixir(第2版)

  • オーム社
4.00
  • (1)
  • (1)
  • (1)
  • (0)
  • (0)
本棚登録 : 29
感想 : 2
本ページはアフィリエイトプログラムによる収益を得ています
  • Amazon.co.jp ・本 (408ページ)
  • / ISBN・EAN: 9784274226373

作品紹介・あらすじ

プログラミング言語Elixirを学ぶ
Elixir(エリクサー)は、並行処理を得意とするプログラミング言語ErlangのVM(エンジン部分)を基盤とし、Erlangよりもなじみやすい文法を採用したプログラミング言語です。
本書は、世界的なRubyプログラマであるDave Thomas氏が書いた、プログラミング言語Elixirの本格的解説書“Programming Elixir 1.6” (Pragmatic Bookshelf, 2018) の日本語訳です。
通常のプログラミングから、並行処理、さらなる応用へと順を追って進む構成になっています。本書を読むことで、Elixirらしいプログラミングを学ぶことができます。

感想・レビュー・書評

並び替え
表示形式
表示件数
絞り込み
  • # 1周目 読み終えた

    この本自体は、わかりやすく書かれていて、1冊めに最適な本であることは間違いない。関数型言語の中では、Elixirの言語自体はそれほど習得するのが難しい言語ではないという感想を持った。ただ、やはりOPTによる並行プログラミングの周りを十分に理解しないまま使い続けるのは難しく、やはり難しい部類に入るのではないかとも思った。それは、言語が難しいわけではなく、並行処理の難しい部分を一身に受けているからで、比較的やさしいとはいえ、本来難しい問題を扱うのだから、完全に覆い隠して簡単なように見せかけることはできないといったところだろう。

    最初は読みやすかったのだけど、パート2の並行プログラミングから集中力が途切れてきて、練習問題もスキップして、手も動かさず読み進めるだけになってしまった。この本の趣旨は、「Elixirを網羅することではなく、ハイライトを取り上げて、Elixirでアプリケーションのコーディングを始めるのに十分な情報を提供しようとするものだ」とある。自分の場合、そこまでは到達できなかった。もともとElixirに対してそこまで関心があったわけではなく、そもそも店頭でこの本を見かけてElixirという名前を知ったのであり、ちょっと触ってみよう程度だったので、本気で取り組んだわけでもなかった。その分、あまり時間をかけずに読み終えることができて、大体の雰囲気は伝わってきた。はなから1周目ですべてを理解しようとは思っていなくて、アプリケーションを書く機会にまた読み直すことにすれば良い。


    ## 付録を読んだ

    付録A「例外:raise、try、catch、throw」
    例外は、rescueで捕まえるものと、catchで捕まえるものの、2種類あるようだ。オブジェクト指向言語によくある例外とさほど違いはない。Elixirでは例外はめったに使われることがないようで、今は例外の存在を無視した方がいいとアドバイスされている。代わりにプロセスに隔離する。付録に追いやられてしまうくらいなので、確かに重要ではないのだろう。

    付録B「型仕様と型チェック」
    付録に追いやられている割に、やや込み入った濃い内容になっている。そこそこ重要なことが書かれているのではないかという気がしている。

    付録C「参考文献」
    Programming Erlang 2nd edition 1冊のみ。実にシンプルだ。

    付録D「Elixir 1.6以降の状況と開発運用の実態」
    タイトル通りの内容。特に、20章でもやったDistilleryを使っていたリリースがElixirに取り込まれて、mix releaseとできるようになったようだ。これについてざっとその手順が書かれている。最後に、Webアプリケーションのデリバリーについて書かれていて、今後はKubernetesのようなコンテナオーケストレーションがデファクトスタンダードになっていくだろうと書かれている。

    付録E「日本語版に寄せて」
    Elixir作者と著者のコメントが書かれている。冒頭に持ってきた方がいいんじゃないかという気がしないでもない。


    ## 25章を読んだ

    「かっこいい機能のいろいろ」

    これが最後の章。自前のシジルの定義と、アンブレラプロジェクトでサブプロジェクトとしてひとつにまとめる機能の紹介。いろいろとあるけど、そんなに多くはない。


    ## 24章を読んだ

    「プロトコル―ポリモーフィック関数」

    ビヘイビアとよく似ている。型によって異なる挙動を取るようにするという点で、やや目的が異なる。プロトコルの特徴は、プロトコルの定義と実装は切り離されているのと、既存のある型について、その型の定義でプロトコルを実装するように書かれていなくても、別の場所で、後付けでプロトコルの実装を追加できるということだろう。同じような機能を提供する言語はたくさんあるように思える。それらは、言語の型システムの柱となる重要なもので、本でこんな終わりの章で扱われるようなものではない。Elixirの場合どうなのだろう。一見とても重要なことのように思えるが。


    ## 23章を読んだ

    「モジュールのリンク:ビヘイビアとuse」

    use GenSever が何をやっているかについて。これは、GenSeverが決めた特定の名前の関数を定義することを、useする側に要求することを意味する。それだけではなく、デフォルトの定義を与えることもできて、その場合、useするだけで、そのモジュールが提供するものがつかえるようになる。この章の例では、defをマクロで置き換えるということで、すべての関数の呼び出しの前後にトレースメッセージを出力させることをやってのけている。オブジェクト指向言語の継承とちょっと近い趣があるが、使用感は全く違ってきそうだ。


    ## 22章を読んだ

    「マクロとコードの評価」

    マクロを使いこなすには、その言語の正確な理解と創造性が必要になる、と思っている。あまり言語の細部を深堀りするタイプではないし、創造性もないので、マクロは苦手だ。最近の、モダンな言語は多くが何らかのマクロをサポートしている。これらは、便利な機能というよりも、メタプログラミングによって、言語の枠を超えて作者の思いのまま表現を可能とさせたり、小さな特定用途の言語、DSLを提供することを可能としたりする。特にライブラリを開発する場合に有用だ。ライブラリよりもアプリケーションの開発に関心があるのも、積極的にマクロをマスターしたい気になれない理由の一つなのかと思う。それにしたってどこかで一度きっかり使い込んで、苦手意識を払拭したいという気持ちがある。


    ## 21章を読んだ

    「タスクとエージェント」

    spawnによる低レベルな並行処理と、OTPによるヘビーなアーキテクチャの間を埋める、ちょうどよい感じの並行処理をを提供する。このパートのタイトルである並行プログラミングに対して、最初に想像していたのがちょうどこのタスクとエージェントくらいのものだった。OTPに面食らった感じで、こんなにややこしいことをしないといけないのかと思っていたところ、ちゃんと割と普通の感じのものも提供されているようで安心した。タスクとエージェントもOTPによって動作するのは変わりないけど、従来の手法しか知らないので、こちらの方がずっと親しみを感じた。後に紹介されているが、まずこちらから、段階を追ってより高度なOTPになれていくほうが良いだろう。


    ## 20章を読んだ

    「OPT:アプリケーション」

    OTPの文脈では、アプリケーションという言葉の意味がかなり異なる。コンポーネントとかサービスと解釈すると良いようだ。それであっても、アプリケーションを動かす、のように使っても、それほど今までの意味とかけ離れたようなことにはならない。この章の課題は、OTPアプリケーションをデプロイすることになる。特に、現在稼働中のアプリケーションを停止させることなく、新しいバージョンのアプリケーションに置き換えることに注目する。Distilleryというリリースマネージャがそれをやってくれる。コードを置き換えるのはもちろん、現在のアプリケーションの状態、データを維持したままアップグレードが可能になる。逆に、ダウングレードもできる。この章の簡単な例だけでは、現実のあらゆる要望に答えるものかどうかはわからないが、Erlangの実績からすれば、おそらく可能なのだろうと思わされる。


    ## 19章を読んだ

    「さらに複雑な例」

    ファイルツリーを辿って、重複するファイルを探すアプリケーションの例。これだけ聞くとよくありそうな課題のように思えるが、要件をきっちり見直すと、単純な問題とは言えない。特に、実行時間を短縮するために並行処理は必須である。並行処理も伝統的な並行処理プログラミングとは、少なくとも表面的には、全く異なっている。OTPサーバーとOTPスーバーバイザを複数活用していて、大掛かりすぎるようにも思えなくもない。しかし、個々のサーバーはコンパクトで、その役割と責任もきっかり限定されていて、堅牢そうな雰囲気が漂っている。ここまででは、OTPは、Elixirに備わった一種のフレームワークのように見える。ただし、特殊用途のフレームワークではなく、汎用的でもっと言語とVMに近いところ、低レベルなところで動作するものだが、予め想定されるルールに従ってプログラミングしないといけないところがそう思わさせられる。この章の例にしても、きっちりOTPの基礎を鍛えておかないと、とても無理そうな解答だった。


    ## 18章を読んだ

    「OTP:スーパーバイザ」

    スーパーバイザとはなにか。プロセスを管理する。特に、管理対象として登録したサーバーが死んだとき、自動で再起動させるができることが紹介されている。さらに、サーバーの一部を絶対に死んではないけないプロセスに切り出して、分散させることを僅かなコードの追加で実現している。これだけがスーパーバイザの能力ではないのは、おそらく間違いない。ここでの例のスーパーバイザが提供するのは、可用性であり、本来ならそれは運用の範疇であったところが、Elixirのコードで保証される。そんなふうに解釈した。


    ## 17章を読んだ

    「OTP:サーバ」

    OTPは、Open Telecom Platformのことらしい。電話交換機のために作られていたからそういう名前になっている。今では汎用目的で使用されるので、歴史的な意味の程度しか持たないようだ。OTPは、予め決められたルールに従うことで、何らかの機能を提供する、ある意味フレームワークみたいなものになっている。ここでは、数値を記憶して、要求に応じてその値を返すだけの単純なサーバーが取り上げられている。最初のサーバーなので、基礎を示す目的のための十分にシンプルなものだけど、こんな簡単なんだ!と思えるほど単純ではない。フレームワークみたいなものと言ったけど、おそらく、従来からあるフレームワークによってあらかじめ決められて手順に従ってプログラミングするスタイルとかけ離れたものではない。根本的なところは全然違うかもしれないけど、表面的なところは全く新しい考え方を要求されるものではないと思わされた。


    ## 16章を読んだ

    「ノード―分散システムの要」

    ノードとは何か。大体は動作しているErlang VMのことを指している。複数のノードを実行する例として、ここではiexにノードの名前を指定して起動する方法が示されている。名前が分かれば、お互いを接続するのは簡単にできる。接続先のノードで関数を実行したりできる。複数のノードに接続して、接続先でコードを実行できることは、スレッドやプロセス高いレベル、並行処理を行っていることを意味していて、強力な並行処理を行うアプリケーションのためサポートが得られることを予感させられる。しかし、今の時点では操作がプリミティブ過ぎて、どうやったらこのややこしい機能を使いこなしてまともに稼働するアプリケーションが書けるのか、想像がつかない。もう少し読み進めれば何か感触をつかめるかもしれない。


    ## 15章を読んだ

    「複数のプロセスを使う」

    ここからパートIIにになって、並行プログラミングを扱っていく。Elixirの本領を発揮させるためには、絶対マスターすることが必要になる。嫌でも並行処理をしないといけないので、Elixir環境でプログラミングをすることは、良いトレーニングとなるに違いない。

    プロセスとは、Erlangがサポートするプロセスのことをであって、OSが扱うプロセスとは違う。もっと軽量なものをイメージしておく。実際に100万個のプロセスを走らせる体験をすることができる。それも、普通のコードとあまり変わらない、ちょっと付け足しただけで軽く走らせることができる。だからといって並行プログラミングが簡単ということにはならないが、伝統的なマルチスレッドのプログラミングよりはずっと良い環境であると言える。

    こんな簡単でちゃんと並行プログラミングの修行になるのかというところだが、難しいコーディングテクニックよりも、本質的な並行プログラミングの感性を養うためのトレーニングだと思えば、伝統的な環境に戻ったとしても、何らかプラスに働く効果は得られるだろう。


    ## 14章を読んだ

    「ツールの活用」

    デバッガ、テスト支援、フォーマッタ、依存関係の視覚化、サーバーモニタリングツールの紹介。Elixirの人気が急騰したのは、比較的最近だと思うのだけど、ここで紹介されたのはごく一部であるくらい、快適にプログラミングできるように豊富なツールが作られている。むしろ逆で、豊富なツールが揃っているから、尚、人気を集めたのかもしれない。


    ## 13章を読んだ

    「プロジェクトを構成する」

    GitHubからissueを取ってくるコマンドラインプログラムの作成。Mixというビルドツール、パッケージの依存関係を解決するツールを導入する。Mixは、インターネットを介してパッケージを探して取ってきてくれる。近代的な言語の多くが備えている、例えばnpmのようなものだ。

    Mixを使ったプロジェクトで、実用的なプログラムの作成の一連の流れを体験できる。Mixプロジェクトの構成、テストの書き方、コードをモジュールに分割するためガイド、ElixirとErlangのパッケージリポジトリであるHexから必要なパッケージの探し方など、実際の開発に欠かせない作業を一通り体験する。今までの章で一番楽しい章だった。


    ## 12章を読んだ

    「制御フロー」

    Elixirは関数型言語に分類されるが、一応は、ifなどの実行のパスを制御するものが備わっている。if、unless、cond、case、例外が紹介されている。しかし、できるだけパターンマッチなどを優先するようにして、だらだらと長い分岐を書かないようにすることが推奨されている。この章は短くて重要度も比較的高くないように思える。さらっと流しておいた。


    ## 11章を読んだ

    「文字列とバイナリ」

    「"」で囲まれた文字列と、「'」で囲まれたリテラルは異なる。前者は文字列であり、後者は文字のリストとなっている。また、ビット列を表現するバイナリ型というのがある。前の章で出てきてよくわからなかったのだけど、ここでちゃんと解説が入っている。

    この章の大部分がStringモジュールの関数の一覧に割かれている

    練習問題が少し手の混んだものになってきた。今のままペースで全部こなしていると読み終えるまでに時間がかかりすぎるので、この章からスキップしていくことにして、読み終えてから取り組むことにする。


    ## 10章を読んだ

    「コレクションの処理 ー EnumとStream」

    Elixirはデフォルトで遅延評価を行うようになっていない。遅延評価が欲しければ、Streamモジュールを使えば良い。

    Elixirのリスト内包表記は分かりやすい。

    練習問題に少し手こずった。一応は模範解答に近いものがかけたので満足した。

    ビットストリングとバイトストリングがちらっと再登場している。何なのかわかっていない。


    ## 9章を読んだ

    「寄り道:型とは何か?」

    深遠なる問いを投げかける、2ページだけの短い章。リストとListモジュールは異なる、リストに見えるならばListモジュールの提供する関数を使える。これはダックタイピングに似ているという指摘。


    ## 8章を読んだ

    「マップ、キーワードリスト、セット、構造体」

    入れ子になったマップや構造体へのアクセスはあまり読みやすいとは思えない。なれるまでかなりの訓練が必要になりそうだ。


    ## 7章を読んだ

    「リストと再帰」

    強烈なLisp支持者ではないので、あまり得意ではない。それでも、この章の内容くらいは問題なくこなせて、とても初歩的すぎるように感じるくらいには訓練されているようだ。しかし、軽く見てはいけない。Elixirがいかにうまくリストと再帰を扱うことができるかに注目したい。パターンの中でパターンにマッチされることができるというのは、あまり馴染みのないけど自然な構文でで強力な機能だ。


    ## 6章を読んだ

    「モジュールと名前付き関数」

    面白くなってきた。Erlangのモジュールはシンボルでアクセスすることを知った。例えば :math.sin(:math.pi / 3) のように「:」がつく。iexでMathとタイプすると何かしら存在しているような気配があるのだけど、何なのかわからない。Mathの下には何もないようだ。

    既存のライブラリを検索するには、ErlangとElixir標準とサードパーティーのパッケージリポジトリが対象となる。それぞれ

    + https://www.erlang.org/doc/apps/stdlib/index.html
    + https://hexdocs.pm/elixir/Kernel.html
    + https://hexdocs.pm/

    などを探すことになる。眺めているだけでもなかなか楽しい。


    ## 5章を読んだ

    「無名関数」

    普通の関数より先に無名な関数を扱う本は初めて見た。紹介されているものの大体は関数型言語に期待する通りのものだろう。クロージャーも当然のようにある。ひとつ面白いのは &(IO.puts(&1)) のように書いたとき、Elixirがこれは IO.puts の呼び出しと変わりないということを認識して、包んでいる関数を取り除いてしまうというところだ。それがどういう意味を持つのかは今後明らかになるのだろうか。


    ## 4章を読んだ

    「Elixirの基礎」

    基本的な型、タプルやリストなど。システム型と呼ばれるPID、ポート、リファレンスは何なのかわかっていない。Erlangに由来するものではないかと思われる。それ以外はなんとか大丈夫そうだ。まだ余裕がある。

    この章は前章までより少し長めだった。


    ## 3章を読んだ

    「不変性」

    関数型言語でおなじみの考え方、もはや常識を引き継いでいる。それに加えて、なぜ不変でなければならないのか、値を更新するときにコピーを作成するということで、パフォーマンスに与える影響はどうなのか、ガベージコレクタとの関連性はどうなのか、が書かれている。最終的には、すべてOK、うまく行くという結論になっている。

    すべてタダで手に入るというわけではないだろう。これまでと違った言語でプログラミングするなら、その言語に適した書き方をしないといけない。Elixirの場合、例えば、リストのコピーを作成するといったとき、単純にリストの要素すべてをコピーするのではなく、もっと賢いやり方をする。そういった特徴も把握していないとまともにプログラミングするのは難しいだろう。


    ## 2章を読んだ

    「パターンマッチ」

    「=」について書かれている。伝統的な代入とはかなり異なる。関数型言語でよくある、束縛(バインド)とも異なっている。1 = a としたとき、aに1がバインドされていれば、つまり、それより前で a = 1 が評価されていれば、パスする、といったような初めて出会う考え方だった。これをパターンマッチと呼ぶらしい。

    1章あたりのページが数ページしかなくて、かなりさくさく読めている感じがして良い感じだ。


    ## 第1章を読んだ

    「赤いカプセルをとれ」

    ElixirのインストールとREPLの使い方。インストール方法はURLが貼ってあるだけで、何も書かれていない。リンク先を見ると、どうもOSのパッケージマネージャでインストールするのが基本のようだ。REPLのコマンドははiexという名前になっている。かなり高機能だ。ファイルから実行する手順も書かれている。コマンドの名前はelixirとなっている。HelloWorldはシンプルで IO.puts "Hello, world!" みたいな感じなる。elixirは、コンパイルするだけでなく、スクリプトのように実行することもできるので $ elixir hello.exs といった感じで実行できる。スクリプトのように実行されることを意図したファイルの拡張子を .exs として、コンパイルされることを意図したファイルの拡張子を .ex とする慣習らしい。

    これから読み進めるにあたって大事なことは、楽しむことを忘れないことだ。


    ## 前書きとはじめにを読んだ

    Elixirが開発された最初の動機は、マルチコアへの対応のようだ。CPUがマルチコアへ移行していったことで、ソフトウェアにもそれに対応することが求められていたが、まだ手作業でそれを書かなければいけないような状況だった。そこでErlangのVMに光があたって、その上で動作する、新しく現代的なElixirが生まれた。
    まだ全く手を付けていない段階では、関数型プログラミングを中心に据えた、理想的な言語ように映る。

  • 請求記号 007.64/Th 5

全2件中 1 - 2件を表示

Dave Thomasの作品

  • 話題の本に出会えて、蔵書管理を手軽にできる!ブクログのアプリ AppStoreからダウンロード GooglePlayで手に入れよう
ツイートする
×