2013-03-20 2 views
2

Мне интересно, существует ли способ создать временную переменную в списке параметров настраиваемой структуры управления.объявить переменную в структуре пользовательского контроля в scala

По сути, я хотел бы создать структуру управления, которая выглядит примерно для цикла, где можно создать переменную, т.е., и иметь доступ к I в теле цикла только:

for(i<- 1 to 100) { 
    //loop body can access i here 
} 
//i is not visible outside 

Я бы как сделать что-то подобное в моем коде. Например,

customControl (myVar <- "Task1") { 
    computation(myVar) 
} 

customControl (myVar <- "Task2") { 
    computation(myVar) 
} 
def customControl (taskId:String) ( body: => Any) = { 
    Futures.future { 
     val result = body 

     result match { 
      case Some(x) => 
       logger.info("Executed successfully") 
       x 
      case _ => 
       logger.error(taskId + " failed") 
       None 
     } 

    } 
} 

Прямо сейчас, я обойти эту проблему, объявив переменную вне структуры таможенного контроля, которая не выглядит очень элегантно.

val myVar = "Task1" 
customControl { 
    computation(myVar) 
} 

val myVar2 = "Task2"  
customControl { 
    computation(myVar2) 
} 
+0

Должно быть возможно написать макрос, чтобы сделать это, используя нетипизированные макросы. У меня нет времени писать это сейчас, но основная идея заключалась бы в том, чтобы иметь макрос с двумя списками параметров, которые будут переписываться в один блок, помещая привязку в начале второго блока. Я начал делать что-то простое, называемое [scala-where] (https://github.com/nc6/scala-where), которое может дать вам представление о том, с чего начать. – Impredicative

ответ

2

Вы могли бы сделать что-то вроде этого:

import scala.actors.Futures 

def custom(t: String)(f: String => Any) = { 
    Futures.future { 
    val result = f(t) 

    result match { 
     case Some(x) => 
     println("Executed successfully") 
     x 
     case _ => 
     println(t + " failed") 
     None 
    } 

    } 
} 

И тогда вы можете получить синтаксис, как это, что не то, что вы просили, но избавляет вас объявить переменную на отдельной строке:

scala> custom("ss") { myvar => println("in custom " + myvar); myvar + "x" } 
res7: scala.actors.Future[Any] = <function0> 
in custom ss 
ss failed 

scala> custom("ss") { myvar => println("in custom " + myvar); Some(myvar + "x") } 
in custom ss 
Executed successfully 
res8: scala.actors.Future[Any] = <function0> 

scala> 
2

Обратите внимание, что встроенный в for (x <- expr) body это просто синтаксический сахар для

expr foreach (x => body) 

Таким образом, можно было бы добиться того, что вы хотите (используя существующий for синтаксис), определив обычай foreach метод.

Также обратите внимание, что уже существует метод foreach, который применяется к строкам. Вы могли бы сделать что-то вроде этого:

case class T(t: String) { 
    def foreach(f: String => Unit): Unit = f(t) 
} 

Примечание: Вы можете также изменить тип результата f выше от Unit до Any, и она будет работать.

Что позволит вам сделать что-то вроде

for (x <- T("test")) 
    print(x) 

Это просто тривиальное (и бесполезное) пример, так как теперь for (x <- T(y)) f(x) просто сокращает (или, скорее, «enlongishes») f(y). Но, конечно, изменив аргумент f в приведенном выше определении foreach от String к чему-то другому и выполняя соответствующий перевод из строки t в этот тип, вы могли бы получить более полезные эффекты.

Смежные вопросы