Неявное преобразование в Выполнимый?

Как осуществление, я пытался создать неявное преобразование, которое примет функцию и произведет a Runnable. Тем путем Вы могли назвать методы Java, которые принимают Runnable объекты и используют их как закрытия.

Неявное преобразование достаточно легко:

    implicit def funToRunnable(fun : Unit) = new Runnable() { def run = fun }

Однако я не знаю, как назвать его. Как Вы передаете в функции без аргументов, которая возвращает Единицу, не имея его быть оцененной сразу? Например, я хотел бы, чтобы следующее распечатало "12", но вместо этого это печатает "21" потому что print("2") оценен сразу.

    var savedFun : Runnable = null
    def save(r : Runnable) = { savedFun = r }

    save(print("2"))
    print("1")
    savedFun.run()

Как я говорю компилятору рассматривать print("2") как тело функции, не чего-то, чтобы быть оцененным сразу? Некоторые возможности я попробовал, такой как

    save(() => print("2"))

или

    save(=> print("2"))

не легальный синтаксис.

17
задан demongolem 7 March 2017 в 17:21
поделиться

3 ответа

Интересно, что таким образом можно выполнить код, который получает Runnable и передает ему закрытие.

See:

scala> new Thread( ()  => print( "Hello" ) ).start()
<console>:5: error: overloaded method constructor Thread with alternatives (java.lang.ThreadGroup,java.lang.Runnable,java.lang.String,Long)java.lang.Thread <and> (java.lang.ThreadGroup,java.lang.Runnable,java.lang.String)java.lang.Thread <and> (java.lang.Runnable,java.lang.String)java.lang.Thread <and> (java.lang.ThreadGroup,java.lang.String)java.lang.Thread <and> (java.lang.String)ja...
       new Thread( ()  => print( "Hello" ) ).start()


scala> implicit def funcToRunnable( func : () => Unit ) = new Runnable(){ def run() = func() }
funcToRunnable: (() => Unit)java.lang.Object with java.lang.Runnable

scala> def doRun( runnable: Runnable ) = runnable.run
doRun: (Runnable)Unit

scala> doRun( () => print("Hola"))
Hola

scala> new Thread(()=>print("Hello")).start()

scala> Hello
5
ответ дан 30 November 2019 в 11:03
поделиться

arg, только что ответил на свой вопрос. Я неправильно реализовал неявное преобразование. Правильная реализация -

implicit def funToRunnable(fun: () => Unit) = new Runnable() { def run() = fun() }

, и вы называете ее так:

save(() => print("2"))

Это даст "2"

23
ответ дан 30 November 2019 в 11:03
поделиться

Если вы хотите жить опасно, вы можете преобразовать что угодно в работоспособное:

implicit def whateverToRunnable[F](f: => F) = new Runnable() { def run() { f } }

scala> val t = new Thread(println("Hello"))
t: java.lang.Thread = Thread[Thread-2,5,main]

scala> t.start()
Hello

Или вы можете создать свой собственный создатель и запуск потока:

def thread[F](f: => F) = (new Thread( new Runnable() { def run() { f } } )).start

scala> thread { println("Hi"); Thread.sleep(1000); println("Still here!") }
Hi

scala> Still here!

Если вы хотите вернуться поток, затем

def thread[F](f: => F) = {
  val t = new Thread( new Runnable() { def run() { f } } )
  t.start()
  t
}

Но все это, хотя и полезно, возможно, даже менее полезно, чем scala.actors.Futures (проверено только на 2.8):

scala> import scala.actors.Futures

scala> val x = Futures.future { Thread.sleep(10000); "Done!" }
x: scala.actors.Future[java.lang.String] = <function0>

scala> x.isSet
res0: Boolean = false

scala> x.isSet
res1: Boolean = false

scala> x()   // Waits until the result is ready....
res2: java.lang.String = Done!
12
ответ дан 30 November 2019 в 11:03
поделиться
Другие вопросы по тегам:

Похожие вопросы: