Могу ли я получить AST из живого скала кода? - PullRequest
12 голосов
/ 26 декабря 2009

Я сказал «живой код», потому что я имею в виду не исходные текстовые файлы или исходные строки, а частичные функции / лямбды. (Я знаю, что Ruby1.8 parseTree и C # linq могут это сделать)

рассмотрим частичную функцию f:

val f = (i: Int, j: Int) => (i + j) * 2

Я надеюсь, что есть какой-нибудь инструмент, работающий так:

getBodyAstFrom(f) //=> (Infix('*'), (Infix('+'), Id('i'), Id('j')), Val('2'))

Меня не волнуют семантические вещи (разбор контекста и последствия слишком сложны и ненужны для меня), мне просто нужно дерево синтаксиса из живого кода, возможно ли это?

Могут быть проблемы с проверкой кода других людей, но как насчет моего собственного кода? Возможны ли следующие вещи?

val f = AstFunction(i: Int, j: Int){(i + j) * 2}
f(5, 6) //=> 22
f.ast   //=> (Infix('*'), (Infix('+'), Id('i'), Id('j')), Val('2'))

Кажется, нужно взломать компилятор, хмммм ...

1 Ответ

17 голосов
/ 26 декабря 2009

Сам компилятор - это библиотека, которую вы можете вызвать. Вот как работает REPL. Но хотя вы можете получить дерево (на разных этапах) для строки кода, вы не можете получить его для скомпилированного кода.

За исключением, конечно, если вы используете экспериментальный материал, который может измениться в любой момент или просто прекратит свое существование. В этом случае вы можете попробовать:

scala.reflect.Code.lift(f).tree

И получите:

res17: scala.reflect.Tree = Select(Select(Select(Ident(Field(line26$object,PrefixedType(ThisType(RootSymbol),Class(line26$object)))),Field($iw,PrefixedType(ThisType(Class(line26$object)),Class($iw)))),Field($iw,PrefixedType(ThisType(Class($iw)),Class($iw)))),Method(f,PolyType(List(),List(),AppliedType(PrefixedType(ThisType(Class(scala)),Class(scala.Function2)),List(PrefixedType(ThisType(Class(scala)),Class(scala.Int)), PrefixedType(ThisType(Class(scala)),Class(scala.Int)), PrefixedType(ThisType(Class(scala)),Class(scala.Int)))))))

Помогает ли это или нет ... Вы можете проверить " Уголок компилятора Scala" Мигеля Гарсии".

...