[英]Is there anyway to implement XOR in javascript
我試圖通過以下方式在javascript中實現XOR:
// XOR validation
if ((isEmptyString(firstStr) && !isEmptyString(secondStr)) ||
(!isEmptyString(firstStr) && isEmptyString(secondStr))
{
alert(SOME_VALIDATION_MSG);
return;
}
有沒有更好的方法在JavaScript中執行此操作?
謝謝。
正如其他人所指出的那樣,邏輯XOR對於布爾值來說是不相等的,所以你可以這樣做:
// XOR validation
if( isEmptyString(firstStr) != isEmptyString(secondStr) )
{
alert(SOME_VALIDATION_MSG);
return;
}
我假裝你正在尋找一個邏輯XOR,因為javascript已經有一個按位(^):)
我通常使用一個簡單的三元運算符(我很少使用其中一個):
if ((isEmptyString(firstStr) ? !isEmptyString(secondStr)
: isEmptyString(secondStr))) {
alert(SOME_VALIDATION_MSG);
return;
}
編輯:
致力於@Jeff Meatball Yang 解決方案
if ((!isEmptyString(firstStr) ^ !isEmptyString(secondStr))) {
alert(SOME_VALIDATION_MSG);
return;
}
你否定了值以便在布爾值中轉換它們然后應用按位xor運算符。 也許它不像第一個解決方案那么可維護(或者我可能已經習慣了第一個解決方案)
你正在做一個布爾值的XOR,很容易建模成一個按位XOR(Javascript有):
var a = isEmptyString(firstStr) ? 1 : 0;
var b = isEmptyString(secondStr) ? 1 : 0;
if(a ^ b) { ... }
您可以直接使用按位XOR運算符( ^
):
if (isEmptyString(firstStr) ^ isEmptyString(secondStr)) {
// ...
}
它將適用於您的示例,因為布爾值true
和false
值被轉換為1
和0
因為按位運算符使用32位整數。
該表達式也將返回0
或1
,並且該值將由if
語句強制回布爾值。
您應該知道上述方法發生的類型強制,如果您正在尋找良好的性能,我不建議您使用按位運算符,您也可以使用僅邏輯邏輯來創建一個簡單的函數運營商:
function xor(x, y) {
return (x || y) && !(x && y);
}
if (xor(isEmptyString(firstStr), isEmptyString(secondStr))) {
// ...
}
一種方法更簡單:
if ((x+y) % 2) {
//statement
}
當然假設兩個變量都是真正的布爾值,即1
或0
。
x === y
你會得到一個偶數,所以XOR將為0
。 x !== y
那么你會得到一個奇數,所以XOR將是1
:) 第二種選擇,如果您注意到x != y
計算結果是異或,那么您必須做的就是
if (x != y) {
//statement
}
這將再次評估為異或。 (我更喜歡這個)
當然,一個好主意是將它實現為一個函數,但它只是你的選擇。
希望這兩種方法中的任何一種都能幫到別 我將此答案標記為社區維基,因此可以進行改進。
在javascript中查看XOR的不同實現的這種解釋。
只是在這里總結一些:
if( ( isEmptyString(firstStr) || isEmptyString(secondStr)) && !( isEmptyString(firstStr) && isEmptyString(secondStr)) ) {
alert(SOME_VALIDATION_MSG);
return;
}
要么
if( isEmptyString(firstStr)? !isEmptyString(secondStr): isEmptyString(secondStr)) {
alert(SOME_VALIDATION_MSG);
return;
}
要么
if( (isEmptyString(firstStr) ? 1 : 0 ) ^ (isEmptyString(secondStr) ? 1 : 0 ) ) {
alert(SOME_VALIDATION_MSG);
return;
}
要么
if( !isEmptyString(firstStr)!= !isEmptyString(secondStr)) {
alert(SOME_VALIDATION_MSG);
return;
}
從引用此文章:
不幸的是,JavaScript沒有邏輯XOR運算符。
您可以通過以下方式“模擬”XOR運算符的行為:
if( !foo != !bar ) {
...
}
鏈接的文章討論了幾種替代方法。
假設您正在尋找BOOLEAN XOR,這是一個簡單的實現。
function xor(expr1, expr2){
return ((expr1 || expr2) && !(expr1 && expr2));
}
以上來源於“獨占分離”的定義{任一個,但不是兩個}。
由於布爾值true
和false
在使用按位運算符時分別轉換為1
和0
,因此只要值為布爾值,bitwise-XOR ^
就可以作為邏輯XOR和bitwiseone執行雙重任務( Javascript的“truthy”值不會起作用)。 否定就容易實現這一點!
運營商。
a XOR b
在邏輯上等同於以下(短)表達式列表:
!a ^ !b;
!a != !b;
還有很多其他形式 - 例如!a ? !!b : !b
!a ? !!b : !b
- 但是這兩種模式的優點是只評估a
和b
一次(並且如果a
是假的則不會“短路”,因此不評估b
),而使用三元的形式?:
,或者||
或AND &&
運算符將進行雙重評估或短路。
否定!
兩個語句中的運算符很重要,包括幾個原因:它將所有“truthy”值轉換為布爾值(“” - > false,12 - > true等),以便按位運算符具有可以使用的值,所以不等式!=
運算符只比較每個表達式的真值(如果a
或b
不相等,非空字符串等,則a != b
將無法正常工作),以便每個評估返回一個布爾值結果第一個“真實”的價值。
您可以通過添加雙重否定(或異常, !!a ^ !!b
,仍然等效於XOR)繼續擴展這些表單,但在否定表達式的一部分時要小心。 如果你考慮算術中的分布(其中2(a + b) == 2a + 2b
等),這些形式似乎乍一看“工作”,但實際上從XOR產生不同的真值表( 這些產生與邏輯NXOR類似的結果 ):
!( a ^ b )
!( !!a ^ !!b )
!!a == !!b
那么,XOR的一般形式可能是函數( 真值表小提琴 ):
function xor( a, b ) { return !a ^ !b; }
然后你的具體例子是:
if ( xor( isEmptyString( firstStr ), isEmptyString( secondStr ) ) ) { ... }
或者,如果isEmptyString
僅返回布爾值,並且您不需要通用的xor
函數,則只需:
if ( isEmptyString( firstStr ) ^ isEmptyString( secondStr ) ) { ... }
XOR只是意味着“這兩個布爾值是不同的嗎?”。 因此:
if (!!isEmptyString(firstStr) != !!isEmptyString(secondStr)) {
// ...
}
!!
s只是為了保證!=
運算符比較兩個真正的布爾值,因為可以想象isEmptyString()
返回其他內容(如null
為null
,或者字符串本身為true)。
我希望這將是最短最干凈的
function xor(x,y){return true==(x!==y);}
這適用於任何類型
Javascript沒有邏輯XOR運算符,因此您的構造似乎是合理的。 如果它是數字,那么你可以使用^即按位XOR運算符。
干杯
這是一個可以容納兩個到多個參數的XOR
function XOR() {
for (var i = 1; i < arguments.length; i++)
if ( arguments[0] != arguments[i] )
return false;
return true;
}
使用示例:
if ( XOR( isEmptyString(firstStr), isEmptyString(secondStr) ) ) {
alert(SOME_VALIDATION_MSG);
return;
}
這是一個XOR函數,它接受可變數量的參數(包括兩個)。 爭論只需要true
或false
,不是true
或false
。
function xor() {
for (var i=arguments.length-1, trueCount=0; i>=0; --i)
if (arguments[i])
++trueCount;
return trueCount & 1;
}
在我的2007 MacBook上的Chrome上,它在14 ns內運行三個參數。 奇怪的是,這個略有不同的版本需要2935 ns的三個參數:
function xorSlow() {
for (var i=arguments.length-1, result=false; i>=0; --i)
if (arguments[i])
result ^= true;
return result;
}
試試這個: function xor(x,y) var result = x || y if (x === y) { result = false } return result }
function xor(x,y) var result = x || y if (x === y) { result = false } return result }
有幾種方法,但三元方法(a?!b:b)似乎表現最佳。 此外,如果您需要經常使用xor,設置Boolean.prototype.xor似乎是一個選項。
你可以這樣做:
Math.abs( isEmptyString(firstStr) - isEmptyString(secondStr) )
結果是XOR運算的結果。
@george,我喜歡你的功能,因為它能夠接收2個以上的操作數。 我有一點點改進,使它恢復得更快:
function xor() {
for (var i=arguments.length-1, trueCount=0; i>=0; --i)
if (arguments[i]) {
if (trueCount)
return false
++trueCount;
}
return trueCount & 1;
}
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.