Upgrade to Pro — share decks privately, control downloads, hide ads and more …

【解説付き】自作のEsolangでQuineに挑戦してみた

 【解説付き】自作のEsolangでQuineに挑戦してみた

部内の発表資料
自作のEsolang「emojifunge」でQuineに挑戦したので発表。
解説付き。

ten986

July 15, 2022
Tweet

More Decks by ten986

Other Decks in Programming

Transcript

  1. 自作のesolangで
    Quineに挑戦してみた
    5/30 @ten986

    View Slide

  2. 前提知識: esolangとは
    ● esolang: 難解プログラミング言語
    ● 基本的に、実用性を目指さないジョーク言語
    ● 見た目にユニークなもの、難しさを極めたもの、
    ゴルフに特化したもの、などさまざま
    ● 例: Brainfuck による Hello, world!

    View Slide

  3. 前提知識: Quineとは
    ● Quine: ソースコードと出力が一致するコード
    ● Ruby による Quine が有名
    ● これはソースコードと出力が一致する
    ○ eval s="puts'eval s='+s.inspect"

    View Slide

  4. 背景: paiza_run が壊れた話
    ● https://togetter.com/li/1098185
    ● #paiza_run ruby:[rubyのコード] というツイートをす
    ると、@paiza_run が出力をツイートする
    ● [rubyのコード]が、#paiza_run ruby:[rubyのコード] を
    出力するコードである場合、無限ループする
    ● という事件を最近知った

    View Slide

  5. 背景: 例会講座通知が届く
    ● そんな中、例会講座botから
    指名を受ける
    ● ひとまず締切を決めたら
    動くだろうから、5/30に入れる
    ● ネタはどうしたもんか・・・
    ● → esolang で Quine をやればよいのでは!!??

    View Slide

  6. 背景: esolang の Quine について
    ● 調査してみる
    ● KMCの人は強いから聞いたら
    情報くれるやろ(丸投げ)
    ● mametter 氏によるスライドを
    教えてもらう
    ● やべ〜w

    View Slide

  7. 背景: なら自作のesolangで
    ● esolang による Quine には前例があった
    ● そういえば以前にesolangを作ったことがあった
    ● 自作esolangでQuineに挑戦してみよう!!!
    ● そして今に至る......

    View Slide

  8. 自作esolang「emojifunge」
    ● emojiを二次元に配置し、
    ポインタがその上を動く
    スタック指向言語
    ● スタックのネストなど、スタック機能が強力
    ● 命令セットがユニーク
    ● emojiの出力機能も備える
    ● https://github.com/ten986/emojifunge-lang

    View Slide

  9. emojifungeでQuineを作ろう!
    ● 早速ですが、emojifungeでQuineが組めました!
    ● 次のスライドにコードを載せました!
    ● コードの全貌を見てみましょう!

    View Slide

  10. 📜

    View Slide

  11. 📜
    ・・・🤔

    View Slide

  12. emojifungeにはQuine命令があった
    ● emojifunge には Quine をする命令があった
    ● これ1文字書けば、なんとプログラムと出力が一致す
    る!!!!!!
    ● たった 4byte で Quine が実現!!!!!!

    View Slide

  13. 余談: HQ9+
    ● HQ9+ という言語がある
    ● 4命令しかなく、「Q」で
    Quine が実現する
    ● もちろんチューリング完全
    ではない

    View Slide

  14. そういうことではない
    ● Quine は実現したが、求めているものではない
    ● 華麗な、奇妙な実装からくるプログラムの奥深さが
    Quine に求めているもののはず
    ● こんなものでいいのか?

    View Slide

  15. ちゃんと Quine を実装しよう
    ● 📜のようなズルはせずに Quine を実装する
    ● mametter 氏によるスライド のほか、
    angel_p_57氏のWhitespaceのQuineの記事 が
    実装の上で参考になりそう(なった)

    View Slide

  16. ちゃんと実装したものがここに
    ● ちゃんとemojifungeでQuineを実装しました
    ● このために今日朝5時まで作業してた(は?)
    ● 次のスライドに載せる他、gist にも上げました
    ● https://gist.github.com/ten986/fbd05be46d9c750b09
    09af3be6776550

    View Slide

  17. View Slide

  18. View Slide

  19. おめでとうございます
    ● emojifunge で Quine が実現できました
    ○ やったね!
    ● ちゃんと出力も一致している
    ● ちなみに、1行目は約30,000文字あるっぽい(?)

    View Slide

  20. 解説をしていく
    ● 実装できたので、実装解説をします
    ● angel_p_57氏のWhitespaceのQuineの記事
    を参考に、「A, B, C」という各部に分けて解説

    View Slide

  21. A
    B
    C
    Aをコピー
    Aの左を出力
    Aの右を出力

    View Slide

  22. 概要
    ● emojifungeは、codeUnit によるスタックを emoji として扱う
    ○ codeUnit: https://jsprimer.net/basic/string-unicode/
    ○ 0⃣ の codeUnit は [48, 65039, 8419] である
    ○ emojifunge はスタックのネストができる
    ○ [ [48, 65039, 8419], [48, 65039, 8419], [48, 65039, 8419] ] という
    スタックにより、0⃣0⃣0⃣が表せるはず
    ● emojifunge のコードは、emoji + 改行 で表される
    ○ 改行は、長さ0のスタック [] で表すことにする
    ● つまり、スタック列でemojifungeのコードを表すことができる

    View Slide

  23. 概要
    ● 処理順としてはこう
    ● A:2行目以降のコードを表すスタック列を載せる
    ● (このスタック列全体を1つのスタックにまとめ、複製する)
    ● B:スタック列に対し、「そのスタック列を載せるようなemojifungeの
    コード」を出力
    ○ つまり、Aの部分が出力される
    ● C:スタック列に対し、「そのスタック列の表すemoji列」を出力
    ○ つまり、2行目以降が出力される

    View Slide

  24. AとBの対応の補足
    ● Aの先頭は「2行目以降のコードの先頭にある⬇のcodeUnit [11015,
    65039] を載せるコード」
    ● 「11015という数に対して、先頭に 0⃣ を置き、「各桁 ➕」と
    間に「🔟 ✖」、65039についても同様、長さ2のcodeUnitなので2⃣、
    最後に 💌 を置く」と機械的な操作
    ● この「機械的な操作を表すemoji列」をBでは出力する

    View Slide

  25. Bを組む
    ● Aは、2行目以降の内容が確定した後、
    機械的に生成するとよい
    ● すなわち、B以降を組むことになる

    View Slide

  26. Bを組む: 概要
    ● スタック列がある。codeUnitのスタックか空スタックの列
    ● スタック列の長さが0なら終了する
    ● スタック列のトップが空スタックなら
    ○ 空スタックを載せるコードである「📧」を出力
    ● スタック列のトップがcodeUnitのスタックならその中に入る
    ○ codeUnitのスタックの長さが0ならスタックを抜ける
    ○ 数を10進数の各桁に分解する
    ○ 先の「機械的な操作」に当てはめてemojiを出力する
    ○ スタックを抜ける時、「機械的な操作」の長さ部分を出力

    View Slide

  27. Bを組む
    ● スタック列の長さが0なら
    終了する

    View Slide

  28. Bを組む
    ● スタック列のトップが
    空スタックなら
    ○ 空スタックを載せる
    コードである「📧」を
    出力
    ● 📧 のcodeUnitを載せて出力
    するだけ
    ● 「機械的な操作」にならって
    いるが、ならう必要はない

    View Slide

  29. Bを組む
    ● スタック列のトップが
    codeUnitのスタック
    ● 数を10進数の各桁に分解する
    ● うまいことループさせます

    View Slide

  30. Bを組む
    ● 先の「機械的な操作」に
    当てはめてemojiを出力する
    ● 11015という数に対して、
    先頭に 0⃣ を置き、
    「各桁 ➕」と間に「🔟 ✖」
    ● このそれぞれをcodeUnitに
    変換してスタック列を積む
    ● 1つのcodeUnitを作るのも
    大変なんです

    View Slide

  31. Bを組む
    ● スタックを抜ける時、
    「機械的な操作」の
    長さ部分を出力
    ● 長さ2のcodeUnitなので2⃣、
    最後に 💌 を置く
    ● 長さは事前に 📥 という
    命令で退避させてある

    View Slide

  32. Cを組む
    ● Bがあんなのでしたが、Cは簡単です
    ● codeUnitのスタックか空スタックの列かで分岐
    ○ 空スタックなら、改行を出力 🔟🔡
    ○ codeUnitのスタックなら、emojiと見なして出力🔣
    ● 簡単!!!!!!

    View Slide

  33. Aを組む
    ● A以外の部分が組めたら、Aを書く
    ● 2行目以降を入力に、「機械的な操作」を出力する
    コードを別途書く
    ● 30,000文字くらい出力される、手作業は厳禁

    View Slide

  34. 完成!
    ● というわけで Quine が完成しました
    ● 大変でしたね

    View Slide

  35. 今後の展望
    ● やはりWebインタプリタが欲しい
    ○ Quine をせっかく作ったが、手軽に実行できない
    ● emojifungeの謎命令でシュッとした Quine が書きたい
    ○ あまりモチベはないが、ヤバいことはできそう

    View Slide