Google Summer of Code

Per Bothner per@bothner.com
Fri Mar 21 02:56:00 GMT 2014


On 03/20/2014 12:48 PM, Andrea Bernardini wrote:
> Il giorno Sun, 16 Mar 2014 23:26:08 -0700
> Per Bothner <per@bothner.com> ha scritto:
>
>>> I created a Case class in kawa.lang. It is an abstract class, so we
>>> can generate a specialized matchKey method for each type of key
>>> (String, Enums, etc.):
>>
>> That doesn't sound right.  How would you decide which kind of key you
>> have until you expand it?  In general you may not know until you do
>> type-inference/-propagation, which happens in the (awkwardly-named)
>> InlineCalls phase.
>
> Ok, so now I'm wondering if it is possible to use the same concepts
> described in "Rapid case dispatch in Scheme" in the compile method of
> CaseExp. That is, to use dispatch on the type and index/clause mapping
> in Java to generate optimized bytecode.

It is certainly possible, but using a type-specific Case Syntax class
doesn't seem practical.  It's better to do type-specific analysis later.
It may be possible in the Syntax class to partition the clauses depending
on the type of the literal, but I would object to that.  It isn't
extensible, since it would be hard to add new case-like forms with
evaluated expression - I would much rather that any type-based 
classification
be done *after* constant-folding and type propation - i.e. in or
after the InlineCalls phase.

I.e. Case Syntax class should not look at the types of the sub-expressions,
just the syntax, and from that assemble a CaseExp.

>>> An other thing I didn't understand yet is where and how this two
>>> classes should be used in the rest of the code.
>>
>> You don't actually need a Case Syntax class.  You can create the
>> CaseExp object directly using Scheme code.  Look at how try-finally
>> (in syntax,scm) creates a TryExp, or how if (in prim_syntax.scm)
>> creates an IfExp.
>
> I came to this:
>
>> public class CaseExp extends Expression {
>> 	
>> 	public CaseExp(Expression key, Expression clauses) {
>> 		System.out.print("Case Expression\n");
>> 	}
>>
>> 	public CaseExp(Expression key, Expression clauses,
>> 			Expression elseClause , Boolean isLambdaForm) {
>> 		System.out.print("Case Expression with else
>> 	clause"+...));
>> 	}
>
>> (define-rewrite-syntax case
>>   (lambda (x)
>>     (syntax-case x (else =>)
>>        ((_ case-key case-clause ... (else => case-else-lambda))
>>        (make <it.polimi.kawacase.CaseExp>
>>          (syntax->expression (syntax case-key))
>>          (syntax->expression (syntax (case-clause ...)))
>>          (syntax->expression (syntax case-else-lambda))
>>          #t))
>>       ((_ case-key case-clause ... (else case-else))
>>        (make <it.polimi.kawacase.CaseExp>
>>          (syntax->expression (syntax case-key))
>>          (syntax->expression (syntax (case-clause ...)))
>>          (syntax->expression (syntax case-else))
>>          #f))
>>       ((_ case-key case-clause ...)
>>        (make <it.polimi.kawacase.CaseExp>
>>          (syntax->expression (syntax case-key))
>>          (syntax->expression (syntax (case-clause ...))))))))

That's the right basic idea.  However, 'clauses' is not an expression;
it's not a set of expressions.  Perhaps best to try something similar to
how TryExpr contains a set of CatchClauses.

If CaseClause extends LetExp in the same way as CatchClause, then
you can translate '=> expression' as something like
   '(let ((dummy (match ...))) (expression dummy))'


> Am I on the right track? Now I have to study how to generate the
> bytecode, obviously at the current state the generated code does
> nothing.

You're on teh right track, but I suggest introducing a CaseClause type.

-- 
	--Per Bothner
per@bothner.com   http://per.bothner.com/



More information about the Kawa mailing list