Upgrade to Pro
— share decks privately, control downloads, hide ads and more …
Speaker Deck
Sign up for free
Menu
Search
Features
All features
Private URLs
Password Protection
Custom URLS
Scheduled publishing
Remove Branding
Restrict embedding
Deck Collections
Notes
Features
All features
Private URLs
Password Protection
Custom URLS
Scheduled publishing
Remove Branding
Restrict embedding
Deck Collections
Notes
Explore
Featured decks
Featured speakers
Programming
Technology
Storyboards
Explore
Featured decks
Featured speakers
Programming
Technology
Storyboards
Pricing
Search
Sign in
Sign up for free
ユーザが構文を自由に変更できるプログラミング言語
Search
Akama Hitoshi
March 30, 2016
Programming
7.7k
2
Share
Embed
Copy iframe code
Copy JS code
Copy link
Start on current slide
ユーザが構文を自由に変更できるプログラミング言語
第5期サイボウズ・ラボユース成果報告会
言語処理系ゼミ
Akama Hitoshi
March 30, 2016
More Decks by Akama Hitoshi
See All by Akama Hitoshi
20年ものの巨大レガシープロダクトを PHP 8.0にアップデートした際の対策と得られた知見
akamah
7
6.9k
プラレールで作る論理回路
akamah
0
3.3k
Other Decks in Programming
See All in Programming
Findy - エンジニア向け会社紹介/Findy Company Deck
findyinc
6
400k
Unity6 URPによる海底をテーマにしたVJシステムの解説 | Unity Shader 完全に理解した 勉強会
gam0022
0
350
Atomic Design, Enforced: Scaling Mobile Design Systems (next.app devCon / droidCon Berlin 2026)
steliosf
PRO
0
160
なぜCTOを降りてFDEを選んだのか?〜なぜプロダクト企業がFDEで顧客の現場に踏み込むのか〜
gonta
1
180
APNsからLive Activityを開始する話
yumnumm
0
160
Compiling a real-world CLI tool to native with Static Hermes
tmikov2023
0
110
すこし踏み込む CancellationToken
htkym
2
1.7k
AIに “答え“を書かせるのを やめてみた
___akari11
0
110
IBM Bob でAI駆動開発『QC-Playbook』
ichirokano2
0
110
Embedded Swiftで作る自作USBデバイス によるiOSデバイスの自動テスト / iOSDC Japan 2026 glassfiber
glassfiber
0
320
Vue Fes Japan 2026 タイムテーブル徹底解説
448jp
1
650
複雑なUIコンポーネントとの ⻑い付き合い⽅:波及するバグからテスト戦略を経て、安全な再設計へ
mixplace
0
330
Featured
See All Featured
A brief & incomplete history of UX Design for the World Wide Web: 1989–2019
jct
2
530
The State of eCommerce SEO: How to Win in Today's Products SERPs - #SEOweek
aleyda
2
12k
Building AI with AI
inesmontani
PRO
1
1.3k
Marketing Yourself as an Engineer | Alaka | Gurzu
gurzu
0
320
Lightning talk: Run Django tests with GitHub Actions
sabderemane
0
300
Raft: Consensus for Rubyists
vanstee
142
7.7k
The Art of Programming - Codeland 2020
erikaheidi
57
14k
Designing for Timeless Needs
cassininazir
1
520
GitHub's CSS Performance
jonrohan
1033
470k
How to Grow Your eCommerce with AI & Automation
katarinadahlin
PRO
2
320
The AI Revolution Will Not Be Monopolized: How open-source beats economies of scale, even for LLMs
inesmontani
PRO
3
3.8k
The Straight Up "How To Draw Better" Workshop
denniskardys
239
140k
Transcript
ユーザが構文を自由に変更できる プログラミング言語 第5期サイボウズラボ・ユース成果報告会 言語処理系ゼミ 2016/03/30 東京工業大学 理学部 情報科学科 赤間 仁志
目的 • 構文を自由に変更できるプログラミング言語を作れないか? • ユーザが新しい構文を導入するメリット: ◦ 簡潔な見た目 ◦ 少ない記述量で望んだ処理を行う •
書いてる途中にどんどん構文が変わっていく言語 ◦ 面白そう ◦ 個人的な興味 2
構文を変更できるとうれしい例 in C • 固定回数のループ文 • forループ特有の条件部分を書かなくてよい for (int i
= 0; i < 10; i++) { printf(“Hello, %d\n”, i); } times(i, 10) { printf(“Hello, %d\n”, i); } Before After 3 #define times(i, n) \ for (int i; i < (n); i++)
構文を変更できる言語の要件 1. 処理系を変更することで構文を変更するのはダメ ◦ ユーザの手によって構文が変更できること 2. 構文を追加することも,削除することもできること ◦ 不要になった構文もユーザの手で削除できる 3.
構文を定義する構文も作成できること ◦ 構文の定義方法もユーザが作成可能 4 画像素材:http://www.irasutoya.com/
プログラミング言語Garbanzo(仮) ver. 2 • 動的型つけ • インタプリタ方式 ◦ いくつかの命令を搭載 •
組み込みの構文は最小限 ◦ ほぼ構文木をそのまま ◦ どんどん構文を拡張可能 5 {“@”: “print”, {“@”: “append”, “left”: “Hello”, “right”: ”World” } } 画像素材:http://www.irasutoya.com/
一般的なインタプリタ 構文解析器 評価器 AST ソース コード 結果 “(3 + 4)
* 6” * 3 4 6 + 42 6
Garbanzoでの構文解析 • 実行にともない,構文解析ルールを書き換える ◦ 文を1つずつ読み込んで実行 • 構文解析器そのものがGarbanzoのプログラム ◦ Garbanzoの評価器の上で動作 •
構文解析ルールはファーストクラスの値 ◦ プログラム内で操作できる 7 プログラム 構文を変更する 宣言・命令 新しい構文で 記述したプログラム 7
実行の流れ 構文解析器 評価器 AST ソース コード 結果 構文解析 実行 ルールの
追加・削除 8
構文の定義 • 組込の構文は,構文木をそのまま書くので,なんでもできる • けど長ったらしい 9 {"@": "set", "object": {"@":
"get", "object": {"@": "get", "object": {"@": "get", "object": {"@": "get", "object": {"@": "getenv" }, "key": "/" }, "key": "parser" }, "key": "sentence" }, "key": "children" }, "key": "newline", "value": {"@": "quote", "value": {"@": "scope", "body": {"0": {"@": "terminal", "string": "\n" } } } } }
自動生成 • 構文の定義をバージョン1のコードで自動生成 ◦ 共通のランタイム • バージョン1(自作言語)でバージョン2(自作言語)の開発 ◦ デバッガなし ◦
リファレンスなし ◦ 質問する相手なし • 生成された構文をGarbanzoの初期構文とする ◦ 標準ライブラリ的な構文 10
自動生成 • 構文の定義をバージョン1のコードで自動生成 ◦ 共通のランタイム • バージョン1(自作言語)でバージョン2(自作言語)の開発 ◦ デバッガなし ◦
リファレンスなし ◦ 質問する相手なし • 生成された構文をGarbanzoの初期構文とする ◦ 標準ライブラリ的な構文 11 ヤバい
初期構文を用いる例 fib = fun(n) if n < 2 n; else
../fib(n - 1) + ../fib(n - 2); end end; /print(fib(7)); 12 ここで利用している構文: • 数値リテラル • 代入 • 匿名関数 • if〜else文 • 加算・減算 • 関数呼び出し • etc.
構文の拡張例(カッコ) paren = block %/tokenize(/terminal("(")); inner = %/parser/expression; %/tokenize(/terminal(")")); inner;
end; /parser/expression/children/paren = paren; 13 ここで利用している構文: • block ~ end • 代入 • 関数呼び出し • etc.
構文を拡張する構文 • 構文の拡張はまだ煩雑 • 構文を拡張する構文を作成 • Schemeのマクロのような,パターンマッチ式での構文 • 構文ルールの優先度(prec)も指定 let:prec
pattern1 pattern2 … patternN := template; • 初期構文を用いて約60行で実装 14
構文を拡張する構文の使用例 • 優先順位をまとめるためのカッコ let:0 “(“ inner:1000 “)” := inner; 例:
(4 + 5) • 添え字つきのアクセス let:15 store:14 “[“ key:1000 “]” := /get(store, key); 例: hoge[“key”] 15
課題 • 構文解析ルールの曖昧さへの対処 ◦ ルールが合成可能な構文解析の方式が必要 • Rubyでプロトタイプを実装したため,極めて低速 ◦ のちのち他の言語で処理系を書き直す •
構文解析エラーのわかりやすさの向上 16 画像素材:http://www.irasutoya.com/
ラボユースでの活動 • プログラミング言語処理系の開発 ◦ プロトタイプ作成による試行錯誤 • 情報処理学会 第57回プログラミング・シンポジウムに参加 ◦ 論文を執筆
◦ 勉強になる 17
まとめ • 構文を拡張可能なプログラミング言語Garbanzo(仮)を紹介 • 構文解析ルールをユーザが動的に追加することで構文を変更 • 構文を定義する構文も作成可能 ◦ 構文の拡張をくり返すことができる •
プログラミング・シンポジウムで発表 ◦ 開発以外でもラボユースの活動を行う ※適当につけた名前なので,カッコいい名前を募集中です GitHub: https://github.com/akamah/garbanzo 18
補足のスライド 19
データ型 • 文字列,数値,真偽値 • 関数 • データストア ◦ 順序をもったハッシュテーブル ◦
構文木の構成などに利用 20
細かな実行の流れ 1. 特別な構文解析ルール sentence に従って入力から読み取る 2. その結果を評価器に入力(eval)する ◦ この時,読み込んだプログラムが構文解析ルールを変更することがある 3.
入力が空になるまで1から2をくり返す 21
構文解析の実際 • 構文解析ルール = Garbanzoのプログラム片 • evalされると,構文解析を実行する • 構文解析専用の命令を評価器に搭載 ◦
terminal: 指定された文字列を読み取る ◦ choice: 与えられた構文解析ルールを順に試す ◦ etc. 22
構文解析器の変更 • いくつかの構文解析ルール(= Garbanzoのプログラム)が既に存在 • これら既に存在したルールの構文木を直接変更 23
Ver. 1による自動生成の例 integer = '/parser/integer = '{ digit = [@:
"quote", value: [@: "oneof", string: "0123456789"]] a = [@: "sub", left: [@: "tocode", string: %digit], right: [@: "tocode", string: "0"]] rest = [@: "many", parser: digit] ten = [@: "sub", left: [@: "tocode", string: "K"], right: [@: "tocode", string: "A"]] "generate"; /foreach([store: rest, func: ^{ n = [@: "sub", left: [@: "tocode", string: value], right: [@: "tocode", string: "0"]] ../a = ../a * ../ten + n }]); a; } 24