PG 中表示式的計算順序

babyyellow發表於2012-10-31
表示式的計算順序,沒有什麼意外的。

()* / + -   >
這個是沒有疑問的,那麼還講什麼呢?


今天看到了這句了:
The order of evaluation of subexpressions is not defined. In particular, the inputs of an operator or function are not necessarily evaluated left-to-right or in any other fixed order.

在一個表示式裡面的字表示式的計算順序是沒有定義的,可認為是亂序的,或者特定的開發人員的設定了。

第一個問題:

例如:

1)   ;  selelct  true  or  (3 >2) ;   

2)   ;  select (3>2) or true  ;

這連個sql是不定價的,根據短路原則, 1) sql中的3>2 是不會執行的, 2) sql中的 (3>2)是一定會執行的 ,
 
這是我們常規認為的從左到右的執行順序下的思考。

pg裡面是沒有定義的。不一定是這個樣子的,所以對於上面的兩個sql 第二個要比第一個安全,即確保函式或者表示式(3 >2) 能夠被計算一次。


第二個問題:

因為子表示式的計算順序的不去定性,引發了第二個問題,

具有副作用的函式是不適合作為複雜表示式的一部分而存在的。

尤 其是認為在where  having 等字句裡的計算是有順序的時候,副作用函式的的使用將更具有危險性的 ,因為這些字句在開發執行計劃的過程中,廣泛的被重新設計,  在這些字句裡的邏輯運算子(AND OR NOT ) ,可能被以任何邏輯運算所允許的方式從新組織和計算。
這個時候,具有副作用的函式,可能會在其中的某個部分發揮他的副作用,從而影響到最終的執行結果。

所以強制安排各個字表示式的執行順序是非常必要的。


例如:

下面的sql

select  * from  t  where x >0 and y/x>1.5 ;  

不一定會確保 y/x 不會發生被零 除的錯誤。

正確的寫法:

select * from  t  where case  when  x > 0  then  y/x >1.5  else  false  end case  ;

當然這個sql 中更適合寫為   y  》1.5*x 。


切記   表示式的計算順序是確定的,但是子表示式的計算順序是麼有定義的


來自 “ ITPUB部落格 ” ,連結:http://blog.itpub.net/133735/viewspace-748018/,如需轉載,請註明出處,否則將追究法律責任。

相關文章