ブログに書いていたものを引っ越してきました。元の記事公開日は 2020-09-18 です。
やっつけなので汚いです。ライフゲームのコンパイルが通ったのでヨシ、という程度の雑なものです。
https://github.com/sonota88/vm2gol-v2-php
自作言語の概要などについてもこちらを参照してください。
大元は Ruby 版なのですが、実質的には Perl版からの移植です。
ベースになっているバージョン: tag:50 のあたり
(追記 2021-09-18: ステップ60 の修正まで適用しました)
作り方はここに全部書いています(Ruby 版のものですが): vm2gol v2 製作メモ
主な部分のサイズ(2021-09-18 現在):
$ wc -l {lexer,parser,codegen}.php lib/utils.php
66 lexer.php
536 parser.php
423 codegen.php
42 lib/utils.php
1067 合計
今回の実験コーナー。
これまで Dart への移植のときに set を不要にし、Java への移植のときに call を不要にし、Perl への移植のときに call_set を不要にしてきました。
これらを全部適用するとどうなるか trial ブランチ
でやってみました。
とりあえず parse_stmt()
の分岐のとこだけ貼ってみます。
<?php
# ...
# if ($t->str_eq("set" )) { return parse_set(); }
# if ($t->str_eq("call" )) { return parse_call(); }
# elseif ($t->str_eq("call_set")) { return parse_call_set(); }
elseif ($t->str_eq("return" )) { return parse_return(); }
elseif ($t->str_eq("while" )) { return parse_while(); }
elseif ($t->str_eq("case" )) { return parse_case(); }
elseif ($t->str_eq("_cmt" )) { return parse_vm_comment(); }
else {
if (
$t->kind_eq("ident")
&& peek(1)->is("sym", "=")
) {
if (
peek(2)->kind_eq("ident")
&& peek(3)->is("sym", "(")
) {
return parse_call_set();
} else {
return parse_set();
}
} elseif (
$t->kind_eq("ident")
&& peek(1)->is("sym", "(")
) {
return parse_call();
} else {
throw not_yet_impl($t);
}
}
個別に試していたときはそれぞれの個別のことだけ考えてやればよかったのが、3つを同時に満たそうとして else に押し込めてとりあえずこうなった、というものです。ちょっと野暮ったいですが peek(n)
で先読みしてやればなんとかなるようです。
funcall を expr に含めるとかするともうちょっとすっきりする気がします。
vgコードはこんな感じ。ここまでやるとかなり普通の言語っぽい(というか JavaScript っぽい)見た目になりますね。
func main() {
var w = 5; // 盤面の幅
var h = 5; // 盤面の高さ
// 初期状態の設定
vram_set(w, 1, 0, 1);
vram_set(w, 2, 1, 1);
vram_set(w, 0, 2, 1);
vram_set(w, 1, 2, 1);
vram_set(w, 2, 2, 1);
var gen_limit = 0;
var gen = 1;
while (gen != gen_limit) {
make_next_gen(w, h);
replace_with_buf();
gen = gen + 1;
}
}
| PHP | github | 2020-09-18 |
-->
記事 | リポジトリ | 日付 |
---|---|---|
Haskell | github | 2021-06-28 |
OCaml | github | 2021-06-26 |
Pascal | github | 2021-05-22 |
Julia | github | 2021-05-03 |
Rust | github | 2021-04-07 |
Crystal | github | 2021-03-27 |
Pric(セルフホスト) | github | 2021-02-21 |
Kotlin | github | 2021-01-14 |
Zig | github | 2021-01-07 |
LibreOffice Basic | github | 2020-12-14 |
Go | github | 2020-09-25 |
C♭ | github | 2020-09-13 |
Perl | github | 2020-09-08 |
C | github | 2020-09-06 |
Java | github | 2020-08-30 |
Dart | github | 2020-08-22 |
Python | github | 2020-08-19 |
TypeScript (Deno) | github | 2020-08-15 |
Crieitは誰でも投稿できるサービスです。 是非記事の投稿をお願いします。どんな軽い内容でも投稿できます。
また、「こんな記事が読みたいけど見つからない!」という方は是非記事投稿リクエストボードへ!
こじんまりと作業ログやメモ、進捗を書き残しておきたい方はボード機能をご利用ください。
ボードとは?
コメント