When I try to build internal DSLs in Scala, I run into a common problem and I haven’t been able to craft a solution. To make things look a bit more like a typical language, I’d like the syntax to look something like this:
model 'Foo {
decl 'Real 'x;
decl 'Real 'y;
}
In practice, there are several issues. The first issue is getting a model object here to take two arguments in this way. If anybody has any ideas, let me know. But what I’ve done instead is to do something a bit more like this:
model('Foo) {
...
}
Where model is now a function which then returns an object with an apply method which then consumes the lambda that follows. That I can live with. I could live with a similar issue inside the lambda as well, so things like decl 'Real 'x or decl('Real,'x) on the inside. But what I want to do is to get the results of all those expressions inside the squiggly braces to get “returned” as a list. In other words, what I want is to write something like this:
model 'Foo {
decl('Real,'x);
decl('Real,'y);
}
where decl(...) evaluates to something of type Declaration and the {...} then evaluates to List[Declaration]. I suspect there is some way of using implicits to do this, but I haven’t been able to find it. In short, I’d like to make:
model 'Foo {
decl('Real,'x);
decl('Real,'y);
}
…evaluate to the equivalent of…
model 'Foo {
decl('Real,'x) ::
decl('Real,'y) ::
Nil
}
Comments or suggestions?
As a first idea, you could try variable arguments lists, which allows you to use commas instead of semi-colons:
Alternatively, you could extend a
traitto get rid of some parentheses and of the commas: