2021-05-23に投稿

Pascalでかんたんな自作言語のコンパイラを書いた

Pascal 初めて書きました。処理系は Free Pascal です。
いつもの通りでライフゲームのコンパイルが通ったのでヨシ、という程度の雑なものです。

https://github.com/sonota88/vm2gol-v2-pascal

移植元

ライフゲームのプログラムだけコンパイルできればOKという簡単なコンパイラです。Ruby 版だとコンパイラ部分だけで 1000行くらい。
ベースになっているバージョンは ステップ 58 のあたり

メモ

主な部分のサイズ(行数)はこんな感じ。

$ wc -l *.pas lib/*.pas
  491 codegen.pas
  153 lexer.pas
  533 parser.pas
  184 lib/json.pas
  222 lib/types.pas
  195 lib/utils.pas
 1778 合計

※ VB はほとんど書いたことがなく、一方 LibreOffice Basic の方は多少書いたことあるので、以下では LibreOffice Basic を挙げていますが、たぶん VB でも大体似た感じだと思います。

ちなみに少し前に LibreOffice Basic で書いたもの:


  • 自分が知っているものの中では C と LibreOffice Basic の中間みたいな印象
    • Pascal + 動的型 → (VB) → LibreOffice Basic という流れ?
  • string 型があって文字列の扱いは C より楽
  • Emacs に pascal-mode をインストール……しなくてもすでに入っていた(インストールした記憶がないので最初から入ってた?)
    • デフォルト設定だとインデントがスペース3つ
  • 今回は fpc をインストールした Docker イメージを使うようにしてみた
  • 処理系に配慮された整理された文法になっていて、たとえば C コンパイラを作るより Pascal コンパイラを作る方がハードルが低そう(コンパイラというか主に構文解析部分?)
    • 教育的、というか元々教育目的として生まれた言語だそう
    • 言語処理系自作に興味がある人は触れておいて損はなさそう
    • 書籍『コンパイラ 作りながら学ぶ』の PL/0' も Pascal 系の言語

Pascal は今まで触れる機会がなくて全然知らない文化圏という意識でいたのですが、実際触ってみると完全に異文化ということもなくて、自分が書いたことのある言語でいえば LibreOffice Basic が近いです(とりあえず見た目は)。

たとえば整数を2つ受け取って足した結果を返す関数は次のようになります。

// Pascal

function add(a : integer; b : integer) : integer;
begin
  add := a + b;
end;
' LibreOffice Basic

function add(a, b)
  add = a + b
end function
  • return 返り値 ではなく 関数名 = 返り値 と書く
  • 返り値の有無で sub(Pascal では procedure) と function を使い分ける
  • 関数・プロシージャ呼び出し時に引数がない場合は括弧を省略可

といったあたりが Pascal 由来と思われます。構造体の扱いも似ているような?

書いているときの感触としては「LibreOffice Basic の変数に型が付いて、文法はなんとなく似ていて、低水準の操作ができる」みたいな感じでした。


LibreOffice Basic 以外でも、JavaScript の with も Pascal 由来かな? とか、Go の := も Pascal 由来かな? とか、 Scala や Rust、Zig など、コロンで区切って型を後置するのも Pascal 由来かな? といった感じで、他の言語への影響と思われる(※確認はしていなくて、あくまで「思われる」という程度)要素がいろいろあって面白かったです。

Kuin の言語仕様の解説にも Pascal への言及がちらほら出てきますね。たとえば「Kuin言語仕様3 演算子」など。

参考

他の言語への移植

記事 リポジトリ 日付
Julia github 2021-05-03
Rust github 2021-04-07
Crystal github 2021-03-27
Kotlin github 2021-01-14
Zig github 2021-01-07
LibreOffice Basic github 2020-12-14
Go github 2020-09-25
PHP github 2020-09-18
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
Originally published at qiita.com
ツイッターでシェア
みんなに共有、忘れないようにメモ

sonota486

Crieitは誰でも投稿できるサービスです。 是非記事の投稿をお願いします。どんな軽い内容でも投稿できます。

また、「こんな記事が読みたいけど見つからない!」という方は是非記事投稿リクエストボードへ!

有料記事を販売できるようになりました!

こじんまりと作業ログやメモ、進捗を書き残しておきたい方はボード機能をご利用ください。
ボードとは?

コメント