Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Is it possible to force named parameters in scala?

Tags:

scala

In some method I would like to force parameters to be named. The reason being autogenerated code for which the order of parameters is unspecified (and will remain that way).

The closest I can get is

private val _forceNamed: Object = new Object()

def doSomething(forceNamed: Object = _forceNamed, arg1: String, arg2: String, ...): Unit = {
  if (forceNamed != _forceNamed) {
    throw Exception(something)
  }

  // actually do stuff
}

However this only fails at runtime, whereas something failing at compile time would be much nicer.

like image 930
Jamie Avatar asked Jan 06 '17 20:01

Jamie


1 Answers

If you want to close the loophole of being able to pass in null, you can use a value class as a guard.

scala> :paste
// Entering paste mode (ctrl-D to finish)

class Foo {
   import Foo._
   def foo(x: Bar = bar, a: String, b: String) = println(a + b)
}

object Foo {
  private[Foo] class Bar(val i: Int) extends AnyVal
  private val bar = new Bar(42)
}

// Exiting paste mode, now interpreting.

defined class Foo
defined object Foo

scala> val f = new Foo
f: Foo = Foo@4a4f9c58

scala> f.foo(null, "", "")
<console>:13: error: type mismatch;
 found   : Null(null)
 required: Foo.Bar
       f.foo(null, "", "")
             ^
like image 161
Jasper-M Avatar answered Oct 23 '22 10:10

Jasper-M