Files
hakorune/docs/development/roadmap/phases/phase-12.7/ancp-specs/sugar-formatter-tool.txt

303 lines
9.1 KiB
Plaintext
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

================================================================================
Nyash 糖衣構文 可逆フォーマッター仕様
2025-09-03
================================================================================
【コンセプト】
極限短縮構文 ⇄ 標準構文の相互変換ツールNyashで実装
================================================================================
1. 基本設計
================================================================================
box NyashFormatter {
mode: FormatterMode // Compact | Standard | Verbose
birth() {
me.mode = FormatterMode.Standard
}
// 短縮 → 標準への展開
expand(code: StringBox) -> StringBox {
code |> tokenize
|> expandSugar
|> format(me.mode)
|> toString
}
// 標準 → 短縮への圧縮
compact(code: StringBox) -> StringBox {
code |> tokenize
|> compactSugar
|> minify
|> toString
}
}
================================================================================
2. 変換規則マッピング
================================================================================
// 糖衣構文の変換ルールを定義
static box SugarRules {
// 暗黙変数の展開
expandImplicit(ast) {
peek ast {
ImplicitVar("$_") => {
// コンテキストから引数名を推論
local argName = inferArgumentName(ast.context)
Identifier(argName)
}
ImplicitVar("$1") => Identifier("_arg1")
ImplicitVar("$2") => Identifier("_arg2")
else => ast
}
}
// パイプラインの展開
expandPipeline(ast) {
peek ast {
Pipeline(expr, func) => {
// x |> f(a,b) → f(a, b, x)
peek func {
Call(name, args) => Call(name, [...args, expr])
PropertyAccess(prop) => PropertyAccess(expr, prop)
else => Call(func, [expr])
}
}
else => ast
}
}
// 短縮演算子の展開
expandOperators(ast) {
peek ast {
MapOp(list, expr) => {
// list /: expr → list.map(expr)
MethodCall(list, "map", [expandLambda(expr)])
}
FilterOp(list, expr) => {
// list \: expr → list.filter(expr)
MethodCall(list, "filter", [expandLambda(expr)])
}
else => ast
}
}
}
================================================================================
3. フォーマットモード
================================================================================
// 3段階の詳細度
enum FormatterMode {
Compact, // 極限短縮
Standard, // 標準的な記法
Verbose // 初心者向け詳細
}
// モード別の変換例
box FormatExamples {
showModes() {
local code = "[$.name for users if $.age > 18]"
print("=== Compact (極限) ===")
print(code)
print("=== Standard (標準) ===")
local standard = formatter.expand(code)
print(standard)
// [user.name for user in users if user.age > 18]
print("=== Verbose (詳細) ===")
local verbose = formatter.expandVerbose(code)
print(verbose)
// local result = new ArrayBox()
// for user in users {
// if user.age > 18 {
// result.push(user.name)
// }
// }
}
}
================================================================================
4. 実装例:主要な糖衣構文の変換
================================================================================
// 1. 暗黙変数
"list /: {$_*2}"
↓ expand
"list.map(fn(item) { return item * 2 })"
// 2. パイプライン
"input |> trim |> upper"
↓ expand
"upper(trim(input))"
// 3. null安全
"user?.profile?.name ?? 'Anonymous'"
↓ expand
"peek user {
null => 'Anonymous'
else => peek user.profile {
null => 'Anonymous'
else => peek user.profile.name {
null => 'Anonymous'
else => user.profile.name
}
}
}"
// 4. キーワード短縮
"l x = 42; ^ x*2"
↓ expand
"local x = 42
return x * 2"
// 5. 演算子セクション
"nums /: (+1)"
↓ expand
"nums.map(fn(x) { return x + 1 })"
// 6. リスト内包
"[x*x for x in nums if x%2==0]"
↓ expand (Standard)
"nums.filter(fn(x) { return x % 2 == 0 })
.map(fn(x) { return x * x })"
↓ expand (Verbose)
"local result = new ArrayBox()
for x in nums {
if x % 2 == 0 {
result.push(x * x)
}
}
result"
================================================================================
5. 使用例:コマンドラインツール
================================================================================
// nyashfmt.hako - フォーマッターCLI
static box Main {
main(args) {
local formatter = new NyashFormatter()
local mode = args[1] ?? "standard"
local file = args[2]
peek mode {
"expand" => {
local code = FileBox.read(file)
local expanded = formatter.expand(code)
print(expanded)
}
"compact" => {
local code = FileBox.read(file)
local compacted = formatter.compact(code)
print(compacted)
}
"check" => {
// 可逆性チェック
local original = FileBox.read(file)
local round = original |> formatter.compact
|> formatter.expand
|> formatter.compact
if round == formatter.compact(original) {
print("✅ 可逆変換OK")
} else {
print("❌ 変換エラー:情報が失われています")
}
}
else => {
print("Usage: nyashfmt [expand|compact|check] <file>")
}
}
}
}
================================================================================
6. エディタ統合
================================================================================
// VSCode/エディタ向けのフォーマッター統合
box EditorFormatter {
// 選択範囲の展開/圧縮
formatSelection(text, mode) {
local formatter = new NyashFormatter()
peek mode {
"toggle" => {
// 自動判定:短縮記法が含まれていれば展開、なければ圧縮
if me.hasShortSyntax(text) {
formatter.expand(text)
} else {
formatter.compact(text)
}
}
"expand" => formatter.expand(text)
"compact" => formatter.compact(text)
else => text
}
}
// ホバー時のツールチップ表示
showExpanded(position) {
local ast = me.getAstAt(position)
local expanded = SugarRules.expandNode(ast)
// ツールチップに展開形を表示
return "展開形: " + expanded.toString()
}
}
================================================================================
7. 学習モード(初心者支援)
================================================================================
box LearningMode {
// 段階的に糖衣構文を導入
suggestSugar(code) {
local suggestions = new ArrayBox()
// パターンマッチで改善可能な箇所を検出
if code.contains("list.map(fn(x) { return") {
suggestions.push({
original: "list.map(fn(x) { return x * 2 })",
sugar: "list /: {$_*2}",
explanation: "/: は map の短縮記法です"
})
}
if code.contains("if x != null") {
suggestions.push({
original: "if x != null { x.method() } else { null }",
sugar: "x?.method()",
explanation: "?. でnullチェックを簡潔に"
})
}
return suggestions
}
}
================================================================================
8. 設定ファイル
================================================================================
// .hakofmt.json - プロジェクト別設定
{
"mode": "standard",
"rules": {
"implicit_variable": true, // $_ を許可
"short_keywords": true, // l, ^, fn を許可
"unicode_operators": false, // λ, → は使わない
"pipeline": true, // |> を許可
"list_comprehension": true, // [...for...] を許可
"operator_sections": true // (+1) を許可
},
"expand_on_save": false, // 保存時に展開
"check_reversibility": true // 可逆性チェック
}
================================================================================