2012-11-06 2 views
11

은 (2.9.2)이 내가 내가 성공적으로 통해이 일을 생각했다스칼라와 스칼라에서

() => Any 

를 액세스 할 때 다른 가치를 제공하는 함수를 만들려고하고 무두질 이름/태닝 솔루션이 :

def byName(theValue : => Any)() : Any = theValue 
val myHolder = byName(myValue)_ 

그래서 내 홀더는 올바른 유형이다. 그러나 나는이 카레 기능을 만드는 과정에서 이름 매개 변수가 평가된다는 것을 알게되었습니다. 다음과 같이하면 대신 작동합니다.

def byName(theValue : => Any) : Any =() => theValue 
val myHolder = byName(myValue) 

나는 currying 프로세스의 일부가 첫 번째 매개 변수 목록을 참조하고 해당 평가를 트리거한다고 결론을 내립니다. 아무도 그것을 확인하거나 왜 또는 여러 매개 변수 목록과 함께 이름 매개 변수를 사용하는 것에 관한 지침이 있는지 설명 할 수 있습니까?

답변

3

이것은 나에게 버그처럼 보입니다. 나는 scala 2.9.1에서이 이상한 행동을 일으킬 수 있었지만 scala 2.10 RC1에서는 그렇지 못했다. 그래서 나는 이것이 어느 시점에서 고쳐 졌다고 생각한다. 스칼라 2.9.1에서

: 스칼라 2.10 - RC1에서

Welcome to Scala version 2.9.1.final (Java HotSpot(TM) Client VM, Java 1.6.0_27). 
Type in expressions to have them evaluated. 
Type :help for more information. 
scala> def byName(theValue : => Any)() : Any = theValue 
byName: (theValue: => Any)()Any 
scala> def myValue: String = { println("Computing myValue"); "hello" } 
myValue: String 
scala> val myHolder = byName(myValue)_ 
Computing myValue 
myHolder:() => Any = <function0> 
scala> myHolder() 
res0: Any = hello 

:

이슈가
Welcome to Scala version 2.10.0-RC1 (Java HotSpot(TM) Client VM, Java 1.6.0_27). 
Type in expressions to have them evaluated. 
Type :help for more information. 

scala> def byName(theValue : => Any)() : Any = theValue 
byName: (theValue: => Any)()Any 
scala> def myValue: String = { println("Computing myValue"); "hello" } 
myValue: String 
scala> val myHolder = byName(myValue)_ 
myHolder:() => Any = <function0> 
scala> myHolder() 
Computing myValue 
res0: Any = hello 
+0

나는 버그가 있다고 믿는다. https://issues.scala-lang.org/browse/SI-302 – Steve

+0

잘 찾아 냈다. 코멘트에서 그것은 scala 2.10-M4에서 고정 된 것으로 보인다. –

+0

완벽 - 설명해 주셔서 감사합니다. –

2

https://issues.scala-lang.org/browse/SI-302 과 개인적으로 https://issues.scala-lang.org/browse/SI-5610

, 나는 무엇을 지금 찾아 "이전"동작이보다 직관적 인 경우 : 부분 적용은 무언가가 적용됨을 의미합니다.

또는

Odersky 그것을 가지고 같이

가 아니, 그건 ETA 확장이 정의 된 방법입니다. 당신은 람다를 랩핑하지 않고 표현식 주위에 을 먼저 평가할 수 있습니다.

반대로, 평가를 강제하는 것은 정지시키기위한 구문을 고안하는 것보다 쉽습니다.

+0

예, 이름 매개 변수의 컨텍스트에서 "적용"이란 의미는 무엇입니까? Function0을 매개 변수로 전달하면 "적용"은 해당 함수를 열심히 평가해야한다는 것을 의미합니까? 자연스러운 대답은 '아니요'이며, 이름 별 매개 변수에 대해 동일한 결론을 갖는 것이 현명하다고 생각합니다. 간단히 말해, 나는 개인적으로 Matt Hellige의 반론에 동의하는 경향이 있습니다. https://issues.scala-lang.org/browse/SI-302?focusedCommentId=39676&page=com.atlassian.jira.plugin.system.issuetabpanels : comment-tabpanel # comment-39676 –

+0

by-name의 스펙은 "사용"이라고합니다. 나에게 f (myValue)는 expr의 결과가 무엇이든간에 myValue를 사용하는 것처럼 보입니다. f가 f (v : V)와 f (v : => V)로 오버로드되면, myValue가 평가되고 첫 번째 f로 전달된다는 것을 알면 알 수 없습니다. (그러나 나는 의미론의 변화에 ​​철저히 반대하지 않았지만, 나에게 오래된 스펙은 다른 퍼즐러만큼 미친 것이 아니며 반 직관적이지 않았다.) –

+0

흠 - 양쪽이 모두 의미가있다. 귀하의 의견에 감사드립니다. –

관련 문제