2014-09-25 2 views
0

Учитывая перегруженную функцию, причем одна принимает функцию как параметр. Этот параметр-функция не имеет аргументов:Scala: Перегруженная функция с функцией как параметр

def func(param:() => Unit): Unit = { 
    param() 
} 

def func(param: Int): Unit = { 
    println(param) 
} 

Призывая func с анонимной функции идеально работает:

func(() => println("it works")) 

Используя простую функцию не удается:

def functionAsParam(): Unit = { 
    println("it works") 
} 

func(functionAsParam) 

Очевидно, что Scala оценивает functionAsParam и не пропускать эту функцию до func. Вопрос: Как я могу (как пользователь библиотеки, которая предоставляет func s) передать не анонимную функцию?

ответ

2

Существует несколько способов сделать это. Либо вы явно передать функцию в качестве параметра:

scala> func(() => functionAsParam) 
it works 

scala> func (functionAsParam _) 
it works 

(Эти два случая несколько отличаются, хотя, в том смысле, что в первом примере, вы построить новую анонимную функцию с другой функцией, а во втором примере, вы указываете, что эта функция не должна еще быть оценена путем добавления _)

Или вы создаете переменную, которая является функцией и передать его:

val fval =() => println("It works") 
scala> func(fval) 
It works 
+1

Я думаю, что ваши слова не совсем правы в паранах. подчеркивание означает «превратить меня в функцию». Оба способа одинаковы. Не уверен, что кто-то будет использовать первый способ, но если они это сделают, они будут использовать parens при вызове для стиля. http://www.scala-lang.org/files/archive/spec/2.11/06-expressions.html#method-values ​​ –

+0

спасибо за комментарии, на самом деле, кто-то, кто делает это первым способом, это я, потому что второй путь чувствует себя менее «интуитивным». – Ashalynd

2

Ошибка возникает из-за того, что вы определили метод, но ваш func ожидает функцию. Да, есть проблема с перегрузкой в ​​scala (в других областях). Чтобы исправить это нужно вручную преобразовать ваш метод в функцию (это называется ет-expantion):

func(functionAsParam _) 

При включении -Xprint:typer вы увидите, что scalac расширяет вам метод в функцию:

val res4: Unit = func({ 
    (() => functionAsParam()) 
}); 
+0

Первое утверждение неверно, в том, что она работает без перегрузка. Eta-expand случается, если он ожидает func, но вы не можете сказать, что не выбирая один из перегруженных символов. –

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