Как добавить метод в объект перечисления Scala? - PullRequest
3 голосов
/ 21 декабря 2009

Я использую Scala 2.8 и определяю перечисление следующим образом:

object Stooges extends Enumeration {
  type Stooge = Value
  val Larry, Curly, Moe = Value
}

И я хочу добавить метод к этому Перечислению, который циклично переходит к «следующей» марионетке. Я могу определить такой метод за пределами Stooges, и он отлично работает в тестовой программе:

def nextStooge(v:Stooges.Stooge):Stooges.Stooge =
  Stooges((v.id+1) % Stooges.values.size)

Что мне действительно нравится, так это добавить этот метод в Stooges, и я попытался сделать это (используя Stooges.Stooge и Stooges.Value). Те, и другие компилируются. Но запускаю такую ​​программу:

import Stooges._
object App extends Application {
  println(Stooges.nextStooge(Larry))
}

выходы:

Exception in thread "main" java.lang.ExceptionInInitializerError
        at demo.App.main(Stooges.scala)
Caused by: java.lang.IllegalArgumentException: wrong number of arguments
        at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
        at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:39)
        at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:25)
        at java.lang.reflect.Method.invoke(Method.java:592)
        at scala.Enumeration$$anonfun$scala$Enumeration$$nameOf$2.apply(Enumeration.scala:176)
        at scala.Enumeration$$anonfun$scala$Enumeration$$nameOf$2.apply(Enumeration.scala:171)
        at scala.collection.TraversableLike$WithFilter$$anonfun$foreach$1.apply(TraversableLike.scala:1200)
        at scala.collection.IndexedSeqLike$class.foreach(IndexedSeqLike.scala:85)
        at scala.collection.mutable.ArrayOps.foreach(ArrayOps.scala:20)
        at scala.collection.TraversableLike$WithFilter.foreach(TraversableLike.scala:1199)
        at scala.Enumeration.scala$Enumeration$$nameOf(Enumeration.scala:171)
        at scala.Enumeration$Val.toString(Enumeration.scala:237)
        at java.lang.String.valueOf(String.java:2615)
        at java.io.PrintStream.print(PrintStream.java:616)
        at java.io.PrintStream.println(PrintStream.java:753)
        at scala.Console$.println(Console.scala:198)
        at scala.Predef$.println(Predef.scala:152)
        at demo.App$.<init>(Stooges.scala:14)
        at demo.App$.<clinit>(Stooges.scala)

Это ошибка или просто плохая идея?

Ответы [ 2 ]

4 голосов
/ 21 декабря 2009

Это работает для меня:

scala> object Stooges extends Enumeration {
     |   type Stooge = Value
     |   val Larry = Value("Larry")
     |   val Curly = Value("Curly")
     |   val Moe = Value("Moe")
     |
     |   def nextStooge(v:Stooges.Stooge) = Stooges((v.id+1) % Stooges.maxId)
     | }
defined module Stooges

scala>

scala> import Stooges._
import Stooges._

scala> nextStooge(Larry)
res0: Stooges.Value = Curly

scala> nextStooge(Curly)
res1: Stooges.Value = Moe

scala> nextStooge(Moe)
res2: Stooges.Value = Larry

Определенно было бы лучше иметь возможность сказать Larry.nextStooge вместо nextStooge(Larry). Я полагаю, вы должны реализовать это с помощью специального запечатанного класса.

2 голосов
/ 21 декабря 2009

Это ошибка. Эта инициализация делает что-то ужасно странное. Я собираюсь открыть тикет (готово, # 2827 ), если его не существует.

...