2012-04-20 5 views
3

스칼라에 논리적 의미를 구현할 가능성이 있는지 궁금합니다. 예를 들어 :스칼라에서 암시 논리 연산자 구현

a implies b 

로 번역 :

!a || b 

abBoolean으로 평가 약간의 표현입니다.

나는 처음에 다음과 같이 시작하지만 a의 값에 상관없이 모두 ab을 평가하기 때문에 그것은 잘못된 접근 방식

implicit def extendedBoolean(a : Boolean) = new { 
    def implies(b : Boolean) = { 
     !a || b 
    } 
    } 

입니다. 정확한 해결책은 a이 참일 때 b만을 평가할 것입니다.

답변

5

통화 별 이름 매개 변수를 사용하려면, 나는 다음과 같은 충분한다고 생각 :

implicit def extendedBoolean(a : Boolean) = new { 
    def implies(b : => Boolean) = { 
     !a || b 
    } 
    } 

설명 : b에 대한 몇 가지 값을 통과해야하지만 것을 원하지 않는

평가 된 표현; 스칼라는 자동으로 표현식을 인수를 취하지 않고 표현식으로 평가하는 함수로 변환 할 수 있습니다. 그러면 implies 연산자가 필요하면 nullary (0 인수) 함수를 평가합니다.

컴파일러는 제공 한 형식 서명 인 => Boolean 때문에이 변환을 수행 할 수 있음을 알고 있습니다. 이 post은 더 자세히 설명되어 있지만 그 제목만으로는 진행되는 작업에 대한 간략한 설명이 있습니다 : "Automatic Type-Dependent Closure Construction".

스칼라의이 기능을 사용하면 다른 언어의 매크로를 사용하여 쉽게 작성할 수있는 제어 구조를 쉽게 작성할 수 있습니다. 하나의 조건문과 하나의 본문 매개 변수를 사용하여 while 루프를 얼마나 쉽게 구현하는지 관찰합니다.

object TargetTest2 extends Application { 
    //type signature not too terribly mysterious 
    def whileLoop(cond: => Boolean)(body: => Unit): Unit = 
    if (cond) { 
     body 
     whileLoop(cond)(body) 
    } 

    //about as easy to use as a plain-old while() loop 
    var i = 10 
    whileLoop (i > 0) { 
    println(i) 
    i -= 1 
    } 
} 
+2

* null 함수 *는 스칼라에서 * call-by-name 인수 *라고합니다. – ziggystar

+1

참. 내가 링크 된 Scala 웹 사이트의 페이지에서 설명하는 것처럼, "소위 _ 이름 별 평가"는 표현식을 nullary 함수로 자동 변환하여 스칼라에서 구현됩니다._how_ 스칼라가 언어 기능을 구현하는 것이 더 흥미롭고 교육적이라고 생각합니다. 스칼라는 이름을 어떻게 사용하는지주의하는 것보다 언어 기능을 구현합니다. – ellisbben

+0

이 이름이 call-by-name 인 경우를 강조하기 위해 편집 됨 – ellisbben

4

b을 평가해야하는 함수로 만들고 싶습니다. 그렇게하면 실제로 액세스 된 경우에만 평가됩니다.

유형을 => Boolean으로 변경하면 어떤 입력도없이 Boolean으로 평가되는 것을 의미합니다.

implicit def extendedBoolean(a: Boolean) = new { 
    def implies(b: => Boolean) = { 
    !a || b 
    } 
} 

는 여기를 사용하는 방법은 다음과 같습니다 atrue 때, b이 (인쇄 "평가")으로 평가된다

scala> true implies { println("evaluated"); true } 
evaluated 
res0: Boolean = true 

scala> false implies { println("evaluated"); true } 
res1: Boolean = true 

알 수 있습니다. 그러나 afalse 일 때 평가되지 않습니다 (인쇄되지 않음).