【書評】コンピュータシステムの理論と実装 第2版（Nand2Tetris）

[O'Reilly Japan - コンピュータシステムの理論と実装 第2版](https://www.oreilly.co.jp/books/9784814400874/)を読んだので，その書評を書きます．合計でかかった時間は123時間でした．

6章以降の実装はGo言語で行い，そのコードは[こちら](https://github.com/Kaichi-Irie/nand2tetris-go)にあります．こちらはGoパッケージとして公開もしており，ドキュメントも公開しています．
また，自分の作ったコンパイラとアセンブラをWeb上で動かせる[Jack Compiler Web](https://myapp-frontend-505229804915.asia-northeast1.run.app/)というWebアプリも作成して公開しています．

## 本書の概要

[公式サイト](URL)の紹介文を引用します。

> コンピュータシステムをゼロから作って学ぶベストセラー書の改訂第2版。コンピュータを理解するための最善の方法はゼロからコンピュータを作ることです。コンピュータの構成要素は、ハードウェア、ソフトウェア、コンパイラ、OSに大別できます。本書では、これらコンピュータの構成要素をひとつずつ組み立てます。具体的には、NANDという電子素子からスタートし、論理ゲート、加算器、CPUを設計します。そして、アセンブラ、仮想マシン、コンパイラ、OSなどを実装しコンピュータを完成させて、最後にその上でアプリケーション（テトリスなど）を動作させます。

第一部はハードウェア，第二部はソフトウェアについて扱っており，それぞれ6章と最後の章の合計13章からなります．各章はおよそ30ページ前後で，各章の終わりに実装課題が設けられています．各トピックが綺麗にまとまっており，読みやすい構成になっています．

## 前提

### 筆者について
- 情報系（数理）の大学院生だが，コンピュータサイエンスについてはあまり詳しくない
  - プログラミングの経験，数理とその関連分野（グラフ理論，最適化，アルゴリズムなど）の知識はある
  - 一方，ネットワーク，データベース，OS, etc.については勉強中．
- PythonやJuliaなど、いくつかのプログラミング言語を学んだことがある

### 読書の背景
- 情報系の大学院への進学が決まり、春休みに少し時間があったため、コンピュータサイエンスを基礎から学んでみることにしました．

### 本書を選んだ理由
- 本書の想定読者は「（言語を問わない）プログラミング経験者」だった
    - 特別な知識がなくても読めるという点が魅力的だった
- それでいて，CPU、アセンブリ言語、コンパイラ、OSなどの幅広い分野をカバーしているため、コンピュータサイエンスの全体像を捉えるのに適していると考えた
- 「Nand2Tetris」という名前が面白そうだった
- 世界中で高い評価を受けている教材だった

## 感想

各章の読書と実装にかかった時間は以下の通りです。合計では94h程度かかりました。実装時間はあくまで目安であり、個人差があると思いますので、参考程度にしてください。特に私は，テストを通すように実装したり，適宜リファクタリングを行ったりしたため，時間がかかりました．

|  章  | 読書時間 | 実装時間 |
| :--: | :------: | :------: |
|  1   |    1h    |   1.5h   |
|  2   |    1h    |    2h    |
|  3   |    1h    |    3h    |
|  4   |    4h    |    3h    |
|  5   |    2h    |    3h    |
|  6   |   2.5h   |    8h    |
|  7   |   1.5h   |   15h    |
|  8   |    3h    |   10h    |
|  9   |   1.5h   |    3h    |
|  10  |    2h    |   22h    |
|  11  |    3h    |   17h    |
|  12  |   1.5h   |   10h    |
|  13  |   0.5h   |    0h    |
| 合計 |  24.5h   |  98.5h   |


### 良かった点
全体を通じて、まず文章が非常にわかりやすく、読みやすかったです。読んでいるだけでも、つい面白くて読み進めてしまいました。また、「最適化には全く立ち入らない」という方針が素晴らしいと感じました。現実のコンピュータを題材にすると、本質的でない仕様や機能に時間を割かれてしまい、理解も難しくなりますが、本書では教育専用にHackコンピュータやJack OSが設計されているため、本質的な部分に集中することができました。

第一部のトピックはハードウェアですが、実装はソフトウェアで完結している点も素晴らしいと思いました。電子工作を実際にするとなるとハードルが高いですが、本書ではシミュレータを使ってハードウェアを理解することができます。

実装課題については、指示が具体的でありながら丁寧すぎず、ちょうど良く自分で作る楽しみを味わえるようになっています。この塩梅が絶妙で、素晴らしいと感じました。ただし、6章のアセンブラなど、ある程度のプログラミング経験がないと自走するのは難しいかもしれません。そのため、あらかじめ不安がある方は、何人かで取り組むと良いかもしれません。

ただ，後半7章以降（第二部ソフトウェアのセクション）の実装課題から，急激に難易度とボリュームが上がったように感じました．本での指示・指定もかなりざっくりしたものになり，読者は設計から計画して，実装を行う必要があります．そのため，かかる時間も急激に増えました．その一方で，実装課題の質は高く，どんどん理解が深まるのを実感できました．逆に言うと，7章以降は特に，前の章の実装課題をしっかりと理解していないと，次の章を読んで理解することが難しくなります．

最後に、Web IDEは非常に使いやすかったです。エディタとして必要な機能も十分に揃えており、視覚的にもわかりやすいようにデザインされています。ただし、後述しますが、CPU Emulatorに関しては挙動がやや不安定で、いくつかissueも報告されているため、その点は注意が必要です。

### イマイチだった点
非常に満足度が高かったのですが、強いて挙げるとすれば、Web IDEのCPU Emulatorの挙動が不安定だった点です．仕様なのかバグなのかがわからないこともありました。最近、いくつかのissueも報告されているので、改善されることを期待しています。自分が直面した問題と関連するGitHub issueを以下に示します。


#### 問題1
Web IDEのROMでは，`@x`のように変数を命名することができない
解決策：ローカルでアセンブリ（`.asm`ファイル）を編集し，それをROMに読み込んで利用する

- `@1`のように直接アドレスを指定することはできました
- 確かに実際には，ROMに直接シンボルを書き込むことはできなくて，ファイル読み込み→アセンブラが翻訳→ROMに書き込むという流れになるから，これは仕様かもしれません
    - 一応，github issueを立ててる人はいました
        - [\[bug\]: CPU EMULATOR FOR ONLINE IDE NOT ACCEPTING ENTRY OF VARIABLES · Issue #554 · nand2tetris/web-ide](https://github.com/nand2tetris/web-ide/issues/554)
#### 問題2
ローカルファイルを読み込むとテストファイルが使えない，および，既存のテストファイルを読み込むと，ROMが初期化される．つまりテストを通せない．

解決策：ローカルファイルを読み込んだのち，自分でRAMにデータを書き込んでユニットテストを行う
- ともにissueが上がっています
    - [\[bug\]: CPU Emulator: Cannot update Mult.asm or test local file with Mult.tst · Issue #551 · nand2tetris/web-ide](https://github.com/nand2tetris/web-ide/issues/551)
    - [\[bug\]: (Safari, CPU Emulator) Clearing the ROM after starting the execution of the test script. · Issue #527 · nand2tetris/web-ide](https://github.com/nand2tetris/web-ide/issues/527)

#### 問題3
selelct local fileで一度ファイルを読み込んだ後に，もう一度読み込もうとすると失敗する．

解決策：ページをリロードする
- これはそこまで致命的ではないですが，やや不便です
- これもissueが上がっています
    - [\[bug\]: Cannot load asm file twice in a row (reproducible) · Issue #544 · nand2tetris/web-ide](https://github.com/nand2tetris/web-ide/issues/544)



### 次に読みたい本
本書ではかなり幅広い分野が扱われていたおかげで、様々な分野に興味を持てるようになりました。
特に，フルスクラッチで何かを作る面白さに夢中になり，ブラウザや，（さらに本格的な）OS，コンパイラの自作にも挑戦したいと思うようになりました．また，本書では教育用のコンピュータやプログラミング言語，OSが扱われていましたが，実際使われているものの仕様や仕組みについても学びたいと思うようになりました．

今，自作系で気になっているのは
- [低レイヤを知りたい人のためのCコンパイラ作成入門](https://www.sigbus.info/compilerbook)
	- 本書では教育用に設計されたJack言語のコンパイラを作りましたが，実際のC言語のコンパイラをCで作ることができる本です．
-  [ゼロからのOS自作入門 \| マイナビブックス](https://book.mynavi.jp/ec/products/detail/id=121220)
  -  みかん本として有名な本で，とても興味がありますが，あまりにボリューミーなので，手を出すのは少し躊躇しています．
-  [［作って学ぶ］OSのしくみⅠ \| 技術評論社](https://gihyo.jp/book/2025/978-4-297-14859-1)
  -  つい最近出版された本で，やはりOS自作できます．が，Rustで書かれているので，まずはRustを学ぶ必要があるということでハードルを感じています．

自作系以外では，以下のような本も気になっています．
- [はじめて読む486 \| 蒲地 輝尚 \|本 \| 通販 \| Amazon](https://amzn.asia/d/0rHYXhB)
  - 本書では教育用に設計されたHackコンピュータを扱っていましたが、実際の486のCPUを学ぶことで、より実践的な知識を得られると思っています．
-  [［試して理解］Linuxのしくみ \| 技術評論社](https://gihyo.jp/book/2022/978-4-297-13148-7)
  -  Linuxのカーネルやシステムコールについて学べる本
  -  GoやPythonで手を動かしながら学べる

## こんな人におすすめ
- プログラミング経験があり、コンピュータサイエンスの基礎を学びたい方
- 情報系出身で、大学で学んだ経験はあるが、いまいち理解が深まらなかった方
  - 点と点が線で繋がるような感覚が得られると思います
- プログラミングを習いたて（または学びたて）の情報系の1,2回生
  - 実習やより高度な内容の講義への接続に役立つと思います

## 他の方の書評
自分が参考にさせていただいた書評を以下に示します。
- [「コンピュータシステムの理論と実装」をやりきりました - Qiita](https://qiita.com/y-meguro/items/dc11c31cc2667aa20b3c#%E5%A4%A7%E5%A4%89%E3%81%A0%E3%81%A3%E3%81%9F%E3%81%A8%E3%81%93%E3%82%8D)
- [Nand2tetrisをGoで実装する \~ アセンブラ編(6章) \~](https://zenn.dev/yukiyada/articles/44805448111905)