概要
mindが、謎なので調べてみた。
練習問題、やってみた。
練習問題
俺cpuをアセンブルを実行する、インタープリタを書け
俺cpu アセンブラ仕様
ニーモニック | 意味 | stackの状態 |
---|---|---|
% | stack-1, stackの剰余を求める。 | 1個減る |
+ | stack-1, stackの加算を求める。 | 1個減る |
/ | stack-1, stackの除算を求める。 | 1個減る |
* | stack-1, stackの乗算を求める。 | 1個減る |
- | stack-1, stackの減算を求める。 | 1個減る |
= | stack-1, stackの等しいを求める。 | 1個減る |
> | stack-1, stackの大を求める。 | 1個減る |
< | stack-1, stackの小を求める。 | 1個減る |
1-255 | stackに整数を積む。 | 1個増える |
set i | 変数iにstackを入れる。 | 1個減る |
get i | stackに、変数iの値を入れる。 | 1個増える |
out | stackを数値で印字する。 | 1個減る |
jz i | stackが真ならiへ飛ぶ。 | 1個減る |
jnz i | stackが偽ならiへ飛ぶ。 | 1個減る |
jmp i | 無条件でiへ飛ぶ。 | 変化無し |
サンプルコード
コードは 40個の 文字列。
コード数は 変数。
スタック1は 変数。
スタック2は 変数。
aは 変数。
bは 変数。
アセンブラとは
コード(コード数)に 入れ
コード数に 1を 加えて コード数に 入れる
。
行検索とは
数1は 変数
数2は 変数
数1に 入れ
数2に 5を 入れ
数2を 返す
。
RUNとは
文字列1は 文字列
単語1は 文字列
単語2は 文字列
数1は 変数
数2は 変数
合否は 変数
nは 変数
スタック1に 0を 入れ
スタック2に 0を 入れ
aに 0を 入れ
bに 0を 入れ
nに 1を 入れ
ここから
もし nが コード数より 大きい
ならば
終り
つぎに
※ コード(n)を 一行表示する
コード(n)を 文字列1に 入れ
文字列1から 単語切り出し 単語1に 入れ
文字列1から 単語切り出し 単語2に 入れ
※ 単語2を 表示する
もし 単語1が 「stop」に 等しい文字列
ならば
打ち切り
つぎに
もし 単語1が 「*」に 等しい文字列
ならば
スタック2と スタック1を 掛けて スタック1に 入れる
つぎに
もし 単語1が 「+」に 等しい文字列
ならば
スタック2と スタック1を 加えて スタック1に 入れる
つぎに
もし 単語1が 「>」に 等しい文字列
ならば
もし スタック1より スタック2が 大きい
ならば
スタック1に 1を 入れる
さもなければ
スタック1に 0を 入れる
つぎに
つぎに
もし 単語1が 「drop」に 等しい文字列
ならば
スタック1に スタック2を 入れる
つぎに
もし 単語1が 「out」に 等しい文字列
ならば
スタック1を 数値表示し 「 」を 表示し
つぎに
もし 単語1が 「ret」に 等しい文字列
ならば
改行し
つぎに
もし 単語1が 「get」に 等しい文字列
ならば
もし 単語2が 「a」に 等しい文字列
ならば
スタック2に スタック1を 入れ
スタック1に aを 入れる
つぎに
もし 単語2が 「b」に 等しい文字列
ならば
スタック2に スタック1を 入れ
スタック1に bを 入れる
つぎに
つぎに
もし 単語1が 「set」に 等しい文字列
ならば
もし 単語2が 「a」に 等しい文字列
ならば
aに スタック1を 入れる
スタック1に スタック2を 入れ
つぎに
もし 単語2が 「b」に 等しい文字列
ならば
bに スタック1を 入れる
スタック1に スタック2を 入れ
つぎに
つぎに
もし 単語1が 「if」に 等しい文字列
ならば
もし スタック1より 0が 小さい
ならば
単語2で 行検索し nに 入れる
つぎに
つぎに
単語1を 数値変換し 数1と 合否に 入れ
もし 合否が 真?
ならば
スタック2に スタック1を 入れ
スタック1に 数1を 入れる
つぎに
nに 1を 加えて nに 入れる
※ スタック1を 数値表示 「,」を 表示し スタック2を 数値表示 「,」を 表示し aを 数値表示し 「,」を 表示し bを 数値表示し 「,」を 表示し nを 数値表示し 改行する
繰り返す
。
メインとは
コードを クリアし
1を コード数に 入れ
「1 」を アセンブラし
「set a」を アセンブラし
「1 」を アセンブラし
「set b」を アセンブラし
「L1 」を アセンブラし
「get a」を アセンブラし
「get b」を アセンブラし
「* 」を アセンブラし
「out 」を アセンブラし
「drop 」を アセンブラし
「get a」を アセンブラし
「1 」を アセンブラし
「+ 」を アセンブラし
「set a」を アセンブラし
「10 」を アセンブラし
「get a」を アセンブラし
「> 」を アセンブラし
「if L1」を アセンブラし
「ret 」を アセンブラし
「get b」を アセンブラし
「1 」を アセンブラし
「+ 」を アセンブラし
「set b」を アセンブラし
「1 」を アセンブラし
「set a」を アセンブラし
「10 」を アセンブラし
「get b」を アセンブラし
「> 」を アセンブラし
「if L1」を アセンブラし
「stop 」を アセンブラし RUNする。
実行結果
>asm
1 2 3 4 5 6 7 8 9
2 4 6 8 10 12 14 16 18
3 6 9 12 15 18 21 24 27
4 8 12 16 20 24 28 32 36
5 10 15 20 25 30 35 40 45
6 12 18 24 30 36 42 48 54
7 14 21 28 35 42 49 56 63
8 16 24 32 40 48 56 64 72
9 18 27 36 45 54 63 72 81
以上。