Frage

Ich habe ein Szenario, in dem ich einige Objekte, die Notwendigkeit, sich voneinander in Referenzen zu nehmen. Die einzige Art, wie ich dies zu kompilieren, ist die Verwendung erhalten kann faul

class A(b:B)
class B(a:A)
lazy val a:A = new A(b)
lazy val b:B = new B(a)

Ich kann das gleiche tun einige Schauspieler verwenden, und bekommen es auch zu kompilieren

    abstract class Message
    case class Message1 extends Message
    case class Message2 extends Message

    class Actor1(otherActor:Actor) extends Actor {
        def act() {
            loop {
                react {
                    case Message1 =>
                        println("received message1")
                        otherActor ! Message2
                    case _ =>
                }
            }
        }
    }

    class Actor2(otherActor:Actor) extends Actor {
        def act() {
            loop {
                react {
                    case Message2 =>
                        println("received message2")
                        otherActor ! Message1
                    case _ =>
                }
            }
        }
    }

    lazy val actor1:Actor = new Actor1(actor2)
    lazy val actor2:Actor = new Actor2(actor1)

Allerdings, wenn ich fügen Sie die folgende:

    actor1.start
    actor2.start
    actor1 ! Message1

ich die folgende Fehlermeldung erhalten:

Exception in thread "main" java.lang.NoClassDefFoundError: com / fictitiousCompany / stackOverflowQuestion / Test Verursacht durch: java.lang.ClassNotFoundException: com.fictitiousCompany.stackOverflowQuestion.Test beim java.net.URLClassLoader $ 1.run (URLClassLoader.java:202) beim java.security.AccessController.doPrivileged (Muttersprache Verfahren) bei java.net.URLClassLoader.findClass (URLClassLoader.java:190) beim java.lang.ClassLoader.loadClass (ClassLoader.java:307) beim sun.misc.Launcher $ AppClassLoader.loadClass (Launcher.java:301) beim java.lang.ClassLoader.loadClass (ClassLoader.java:248)

Ich bin mit dem Scala Eclipse Plugin 2.8.1.

War es hilfreich?

Lösung

Beachten Sie, dass auch Ihr kleineres Beispiel Probleme haben würde (in der REPL):

{
class A(b:B)
class B(a:A)
lazy val a:A = new A(b)
lazy val b:B = new B(a)
a
}
// causes stack overflow error

Sobald a Bedürfnisse daher konstruiert ausgewertet werden, würde es erfordern, B, die A. für diese Arbeit a oder b Um erfordert hätte fertig gebaut.

Unter Verwendung von-namen Parametern ermöglicht es das kleinere Beispiel zu bewerten.

{
class A(b: => B)
class B(a: => A)
lazy val a:A = new A(b)
lazy val b:B = new B(a)
a
}

Beachten Sie sicher, ob das wird auch für die Schauspieler Beispiel arbeiten.

Edit: nach Namen params arbeitete lokal auf 2.8.0. Ich ersetzen Fall Klasse mit dem Objekt loszuwerden einigen deprecation Warnungen zu erhalten und hinzugefügt Startmethoden auf actor1, actor2 und trete das Ganze mit actor1 ! Message1. Abgesehen davon habe ich Schauspieler noch nie benutzt, so dass ich nicht mehr kommentieren. Hier ist, was ich getestet:

import scala.actors._

abstract class Message
object Message1 extends Message
object Message2 extends Message

class Actor1(otherActor: => Actor) extends Actor {
def act() {
    loop {
    react {
        case Message1 =>
        println("received message1")
        otherActor ! Message2
        case _ =>
    }
    }
}
}

class Actor2(otherActor: => Actor) extends Actor {
def act() {
    loop {
    react {
        case Message2 =>
        println("received message2")
        otherActor ! Message1
        case _ =>
    }
    }
}
}

{
  lazy val actor1:Actor = new Actor1(actor2)
  lazy val actor2:Actor = new Actor2(actor1)
  actor1.start
  actor2.start
  actor1 ! Message1
}

Gibt eine Reihe von:

received message1
received message2
Lizenziert unter: CC-BY-SA mit Zuschreibung
Nicht verbunden mit StackOverflow
scroll top