2016-09-10 4 views
0

Я не понимаю этого поведения. Я хочу проверить, находится ли значение в круге, созданном на сетке (в виде массива). Определение двух сторон круга.Значения Итератора в Scala vs кешированные значения с vals

val circleLeft = Vector(5,14,23..) 
val circleRight = Vector(5,16,27,..) 

Я проверяю нижнюю функцию этого условия. С первым:

def insideCircle(idx: Int): Boolean = { 
    val l = circleLeft.toIterator 
    val r = circleRight.toIterator 
    while (l.hasNext && r.hasNext) { 
    if(idx < r.next && idx > l.next) return true 
    } 
    return false 
} 

возвращает всегда верно. При этом второй

def insideCircle(idx: Int): Boolean = { 
    val l = circleLeft.toIterator 
    val r = circleRight.toIterator 
    while (l.hasNext && r.hasNext) { 
    val x1 = r.next 
    val x2 = l.next 
    println(x2,x1) 
    if(idx < x1 && idx > x2) return true 
    } 
    return false 
} 

Он работает должным образом, то есть insideCircle (15) = верно, insideCircle (17) = ложь

Есть ли что-то здесь разные ..?

ответ

4

&& называется методом короткого замыкания (в Scala он реализован с аргументом by-name). В вашем первом примере l.next выполняется только в том случае, если idx < r.next. Во втором примере всегда выполняется l.next.

UPDATE

Я хотел бы предложить более функциональный способ:

def insideCircle(idx: Int): Boolean = { 
    val l = circleLeft.toIterator 
    val r = circleRight.toIterator 
    r.zip(l).find { 
    case (x1, x2) => 
     idx < x1 && idx > x2 
    } 
    .isDefined 
} 
+0

так, чтобы сделать это и условие я должен закрыть два условия между скобками? EDIT: Красивая, спасибо! – LowFieldTheory

+0

Не уверен, что я понимаю ваш вопрос, вам нужно _evaluate_ как '.next' перед вызовом' && '. Сравните '{println (" left "); false} && {println ("right"); true} 'и' {println ("left"); false} & {println ("right"); true} '(' & 'не является методом короткого замыкания) –

+0

« вам нужно оценить оба .nexts перед вызовом && »теперь я понимаю лучше, нормально – LowFieldTheory

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