yacc/bison と非常によく似た happy パーサーを使用して記述された関数型言語コンパイラで、次のルールを使用して、いくつかのコア関数map
、concat
およびをリストに実装しました。filter
Exp:
...
| concat '(' Exp ',' Exp ')' { Concat $3 $5 }
| map '(' Exp ',' Exp ')' { Map $3 $5 }
| filter '(' Exp ',' Exp ')' { Filter $3 $5 }
これは問題なく機能しますが、ほとんどの関数型言語には括弧やコンマがないため、代わりmap(myfun, [1,2,3])
にmap myfun [1,2,3]
. 文法の明らかな変更は次のとおりです。
Exp:
...
| concat Exp Exp { Concat $2 $3 }
| map Exp Exp { Map $2 $3 }
| filter Exp Exp { Filter $2 $3 }
しかし、この変更には多くのreduce-reduce競合が含まれています。コンマと括弧なしで関数呼び出しを解析するにはどうすればよいですか?
私が抽出できた最小の矛盾する文法は次のとおりです。
Exp :
-- Math
Exp '+' Exp { Op $1 Add $3 }
| Exp '-' Exp { Op $1 Sub $3 }
-- Literals
| num { Num $1 }
| '-' num %prec NEGATIVE { Num (-$2) }
-- Lists
| map Exp Exp { Map $2 $3 }
4 つの削減/削減競合が生成されます。ルールのいずれかを削除すると、競合が発生します。興味のある方は、ここに完全な文法があります。