#738 Vararg?

casperbang Wed 9 Sep 2009

Very pleased that Fan did not inherit Java's inability to forward reference an enum value, such that it's possible to build a state machine:

enum State
{
    PLAYING(State.STOPPED), STOPPED(State.PLAYING)

    private new make(State s)
    {
        state := s
    }

    private const State? state
}

However, I'm missing some vararg capability so that it's possible to associate several transitive target states to a source state:

PLAYING(State.STOPPED, State.PAUSED), PAUSED(State.PLAYING, State.STOPPED),...

Is this possible through some other means I'm perhaps just not aware of yet?

Thanks

brian Wed 9 Sep 2009

Fan doesn't support var-args directly, but you can use lists as a poor-man's var-args with very little noise:

Void m(Obj[] args) {...}


m([state1, state2])

Not sure if that answers your question though.

casperbang Wed 9 Sep 2009

Thanks for answering. Indeed, that's a fair compromise at the call-site. A few follow up questions though revolving around the definition-site.

Howcome I get "Non-nullable field state must be assigned in constructor make", when my member field is declared as nullable but now is just a list instead? Are lists non-nullable?

private const State?[] state

Even if non-nullable, shouldn't the compiler be able to infer that my state field IS indeed being set in the constructor?

Last but not least, does that mean then that there's no way to simulate vararg (optional list syntax at call-site) i.e.:

private new make(State[] s)
{
    state := s
}

private new make(State s)
{
    state := [s]
}

...since Fan does not allow method overloading?

tcolar Wed 9 Sep 2009

Maybe you want this: private const State?[]? state for a nullable list of nullable States.

casperbang Wed 9 Sep 2009

Ah, yeah it works with private const State[]? state. Still, shouldn't it work with just private const State[] state too, as is the case when using private final in Java? Even though I assign my field explicitly in my constructor, the compiler gives me "Non-nullable field state must be assigned in constructor make".

brian Wed 9 Sep 2009

Just to clarify:

State?[]   // non-nullable list of nullable states
State[]?   // nullable list of non-nullable states
State?[]?  // nullable list of nullable states

If you desire a strongly typed constructor, then you will have to pick either State or State[]. Although since it is private you could do this:

new (Obj s)
{
  if (s is State)
    state := State[s]
  else
    state := s
}

And then you could pass either a State or a State[].

Login or Signup to reply.