2012-03-02 44 views
10

我最近發現Java(和Scala)包括非短路邏輯運算符&,|^。我以前認爲這些只能用作按位運算符。雖然也許有關於^的爭論,但我想不出使用非短路邏輯運算符的非常好的理由 - 儘管我很確定,我可以設想一個例子。Java/Scala中的非短路邏輯(布爾)運算符有很好的用處嗎?

這些操作符是否有用?他們似乎更容易造成難以捉摸的錯誤。

scala> def foo = { 
    | println("foo") 
    | true 
    | } 
foo: Boolean 

scala> def bar = { 
    | println("bar") 
    | true 
    | } 
bar: Boolean 

scala> foo || bar 
foo 
res5: Boolean = true 

scala> foo | bar 
foo 
bar 
res6: Boolean = true 
+1

不,位運算符只能用於按位運算,恕我直言: – 2012-03-02 21:41:39

+1

這個問題唯一可能的答案是「非短路運算符在不想短路時非常有用」的具體示例。所以真正的問題是「你什麼時候不想短路」? – 2012-03-02 22:48:35

回答

14

如果右側是一個帶有無論您想要執行的副作用(例如日誌記錄)的函數,它們都很有用。但是,我認爲這是一種代碼味道,對下一個人來說肯定是不直觀的。

+1

完全同意,這不應該用真正的代碼來完成。 – 2012-03-02 21:41:20

+0

正如我所說,我可以做一個人爲的例子;-) – schmmd 2012-03-02 21:56:38

8

嗯。我知道如果仔細使用它們,它們對於優化C/C++代碼非常有用。它也可能適用於Java。

C中的主要用途 - 除了實際的位操作之外 - 就是刪除管道延遲。短路操作人員需要分支操作。按位運算符將計算雙方,並消除錯誤預測分支和產生的失速的機會。

+0

我想你不得不平衡成本的攤位與執行代碼,否則不需要運行/影響程序的結果 – dty 2012-03-02 21:54:21

+0

@dty:是的,絕對。請注意「如果使用得當」。 :-) – 2012-03-02 21:56:11

+5

當我寫Guava的'com.google.common.math'時,當第二個條件特別快時,我的基準有時會指出,由於這個原因,非短路操作員比短路操作員更快。 (也就是說,如果我沒有非常詳細的基準測試,我不會做出改變。) – 2012-03-02 23:10:40

0

如果您試圖追蹤答案或輸入某些內容,並且取決於您的非短路布爾運行的兩端。

舉個例子,假設您有:

if(methodA() & methodB()){ 
    //some code 
} 

及一些關鍵代碼運行的methodB()方法中。如果這是一個短路代碼(& &)且methodA()爲false,methodB()將永遠不會運行。

這是我至少可以想到的用途之一。

2

使用非短路布爾運算符意味着操作數有副作用。如果他們沒有副作用,那麼程序員可以使用短路版本而不改變功能。

在用功能風格編寫的代碼中(Scala肯定鼓勵但不要求),副作用表明某些不尋常的事情正在發生。不尋常的事情應該用代碼清楚地表明,而不是像非短路布爾運算符那樣微妙。