2012-04-23 3 views
7

Мне нужно отключить/включить кнопку в зависимости от значения некоторых групп радио. Эти радиостанции заполнены каким-то четким кодом, потому что я использую grails, основу для groovy, которая является надмножеством java. Хорошо, что объяснение должно было сказать, что значения радиостанций определяются как булевы, что естественно, потому что они соответствуют да/нет ответам.Javascript booleans: false && true results in true

Теперь, чтобы отключить/включить эту кнопку, я использую некоторый javascript, но это бананы с булевыми значениями. Как видно из названия государств, на какой-то момент я логичный и между переменной, которая содержит false и другой переменной, которая содержит true

Вот peice проблемного кода:

var actual = true; 
$('.requerido input:radio:checked').each(function() { 
    console.log("actual: " + actual); 
    console.log("value: " + this.value); 
    console.log("actual and value: " + (actual && this.value)); 
    actual = actual && this.value; 
    console.log("actual: " + actual); 
}); 

Как вы можете видеть, я использую console.log для отладки, и это то, что бросается в какой-то момент:

actual: true 
value: true 
actual and value: true 
actual: true 

actual: true 
value: false 
actual and value: false 
actual: false 

actual: false 
value: true 
actual and value: true 
actual: true 

Так истинный & & лОЖЬ == ложь, но ложь & & true == true? Обратите внимание, что значения не имеют кавычек, поэтому они являются логическими значениями (я отлаживаю консоль Chrome, которые представляют строки внутри двойных кавычек, поэтому вы можете различать true и «true»).

Любые идеи?

Кроме того, выполнение ручного сравнения, такого как var x = true && false, всегда работает так, как ожидалось, это juts с переменными, что проблема присутствует.

+0

Поскольку это явно очень странно, я думаю, уменьшить этот пример минимального теста будет полезно для вас. – zmccord

+1

http://twitter.com/#!/mattmight/statuses/191964430312030208 В PHP и JavaScript «==» произносится как «вероятно равно». –

ответ

11

this.value из выбранного вами переключателя ввода на самом деле не является логическим, это строка. Сравнение строк и логических значений может вызвать такие проблемы. Это одна из причин, почему считается, что наилучшей практикой является использование === для сравнения.

См. Этот ВОПРОС ДЛЯ БОЛЬШИХ деталей; JavaScript === vs == : Does it matter which “equal” operator I use?

+0

, если он не является логическим, тогда я предполагаю, что он неявно преобразован в один, потому что консоль печатает true, а не «true» или «true». Кроме того, когда я пытаюсь поместить значение радио внутри метки или любого другого тега html, он не отображается, пока я явно не нажму '.toString()'. Вот почему я предположил, что это булевая строка, а не строка. – GalmWing

+0

Я в конечном итоге отбросил булевы и использовал числа. В качестве урока: в js никогда не используйте booleans, когда значение находится внутри тега HTML. Поскольку в этом ответе утверждается, что реальная проблема «на самом деле не является логической, это строка», я собираюсь принять ее (и извините за задержку loooong). – GalmWing

0

Попробуйте поразеть и & vice &&. Позднее было бы целесообразно в условном сравнении, но не в присвоении значения переменной.

0

Это действительно то, что вы хотите сделать? :

actual = actual && this.value; 

Это то же самое, как:

if (actual) { 
    actual = this.value; 
} 

actual всегда true, как это определено в вашем коде, так actual будет this.value, а не логическое.

+0

Это то, что я на самом деле делаю? 'actual' НЕ всегда истинно, как вы можете видеть в выводе журнала. – GalmWing

1

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

function boolx(tf,val){ 
    var test = tf && val; 
    console.log([tf,val,tf && val,test]); 
} 
tf(true,false); //=> [true,false,false,false] 
tf(false,true); //=> [false,true,false,false] 

Возможно явное преобразование this.value помогает, потому что this.value на самом деле строка:

var actual = true; 
$('.requerido input:radio:checked').each(function() { 
    var val = /true/i.test(this.value); 
    console.log("actual: " + actual); 
    console.log("value: " + val); 
    console.log("actual and value: " + (actual && val)); 
    actual = actual && val; 
    console.log("actual: " + actual); 
}); 
2

Обратите внимание, что && делает следующее:

Возвращает expr1, если его можно преобразовать в false; в противном случае возвращается expr2.

source

Таким образом, в таких случаях, как:

var truish=true;//interchangeable with anything different than 0,"",false,null,undefined,NaN 
var falsish=null;//interchangeable with 0,"",false,null,undefined,NaN 

alert(truish&&falsish);//null (falsish was returned) 

Возвращаемое значение не обязательно логическое, решение это было бы заставить булево !(x&&y)

Поэтому я предполагаю, что что-то подобное происходит

2

если вы пытаетесь вычислить с логическими операторами, помните:

var result = true && "false";// always results (string) "false" 
var result = true && "true";// always results (string) "true" 
var result = false && "true";// always results (boolean) false 
var result = false && "false";// always results (boolean) false 
var result = "true" && true;// always results (boolean) true 
var result = "true" && false;// always results (boolean) false 
var result = "false" && true;// always results (boolean) true 
var result = "false" && false;// always results (boolean) false 
var result = "true" && "true";// always results (string)"true" 
var result = "true" && "false";// always results (string) "false" 
var result = "false" && "true";// always results (string) "true" 
var result = "false" && "false";// always results (string) "false" 

потому что: Javascript судьи первый операнд, если оно истинно, оно вернет второй операнд, либо возвращать ложь; это так же, как:

var first = true 
var second = "false"; 
if (first) { 
    result = second; 
} else { 
    result = false; 
} 

или

result = first ? second : false; 

это путь Javascript логика оператора на самом деле работает. необходимо выполнить строгое сравнение между различными типами переменных:

result = true && (value==="false"); 

строки не пусто, равно (булево) верно, даже «ложь».

и помните, что атрибуты элемента HTML являются «String» s

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