全國最多中醫師線上諮詢網站-台灣中醫網
發文 回覆 瀏覽次數:1325
推到 Plurk!
推到 Facebook!

二個變數的值交換,不用到其他的變數和記憶體!

 
solong
一般會員


發表:1
回覆:3
積分:0
註冊:2003-01-29

發送簡訊給我
#1 引用回覆 回覆 發表時間:2004-01-23 16:06:06 IP:61.70.xxx.xxx 未訂閱
這是我的一個朋友在應徵時所遇到的問題(在所有的題目裡面,算是較難的), 例如有a,b二個int 的變數,a=5,b=10,要讓這二個變數的值交換,但是不能用到其他的變數,也不能占用到其他的記憶體空間! 後來有想到要如何寫
int a=5,b=10;
    a^=b^=a^=b;
這樣的寫法在BCB上執行是可以的,但是我發現同樣的程式碼,在C# 以及在java上執行,出來的結果卻是不一樣,以上面的例子而言, 出來的答案是:
      a=0
      b=5
但是在bcb上執行,出來的結果是我要的
      a=10
      b=5
在VC我就不知道,我沒裝VC,有大大可以解釋為什麼會這樣嗎?
leobxb
一般會員


發表:18
回覆:30
積分:14
註冊:2003-10-02

發送簡訊給我
#2 引用回覆 回覆 發表時間:2004-01-24 11:21:11 IP:211.74.xxx.xxx 未訂閱
solong你好很顯然你已經發現答案了,只是你自己沒發覺. 說明給你聽a^=b的意思為 a=a xor b 相信你已經知道. 而你沒發覺的是BCB的compiler與C# 及java並不相同    BCB的compiler對a^=b^=a^=b;的處理方式為: a=5------>0000 0101 b=10----->0000 1010    從a^=b^=a^=b;後面看過來,先  1.a^=b 再  2.b^=(a^=b) 最後  3.a^= (b^=(a^=b))    所以 1.a^=b-------------->(0000 0101 ^ 0000 1010)=0000 1111 (a=15)   2.b^=(a^=b)--------->(0000 1010 ^ 0000 1111)=0000 0101 (b=5) 3.a^= (b^=(a^=b))--->(0000 1111 ^ 0000 0101)=0000 1010 (a=10) C# 及java的compiler對a^=b^=a^=b;的處理方式為: 1.b^=(a^=b) 2.a^^= (b^=(a^=b)) 所以 1.b^=(a^=b)--------->(0000 1010 ^ 0000 1111)=0000 0101 (b=5) 2.a^= (b^=(a^=b))--->(0000 0101 ^ 0000 0101)=0000 0000 (a=0) 有收穫記得回饋,讓我們台灣跨出程式的出頭天...
solong
一般會員


發表:1
回覆:3
積分:0
註冊:2003-01-29

發送簡訊給我
#3 引用回覆 回覆 發表時間:2004-01-24 17:26:59 IP:61.70.xxx.xxx 未訂閱
可想而知是compiler的不同才會有這樣的結果,只是不知為何c#  or java  它是如何去做運算的 例如這個例子也是一樣 < class="code"> a=5; b=10; a=-(a-=b =a-=b); 一樣是把二個變數交換,在BCB執行正常,二個變數會交換,但是在c#執行出來的結果 a=0 b=5 而且我發現執行到這裡, > …這又是為什麼? 不論是這個方法 > 請問有大大,或是" >
leobxb
一般會員


發表:18
回覆:30
積分:14
註冊:2003-10-02

發送簡訊給我
#4 引用回覆 回覆 發表時間:2004-01-26 14:02:11 IP:211.74.xxx.xxx 未訂閱
solong 你好,說清楚一點... BCB compiler 會將同一行每一次的變數運算存回變數本身 而 C# 以及在java 只會將同一行運算完後再存回最終變數, 這樣明白了嗎... 還有...許多程式並不會因為你個人的想法認為正確,而執行 就一定正確,有時會因為程式的差異,或延遲時間的不同,而導 致程式執行的錯誤,這些都是需要靠經驗累積的...不然程式 設計師有那麼好當嗎? ps:已有正確的收到問題解答時,記得給分.那是對回答者的一種 肯定,不然最後會沒人願意回答了,這可是對大家一種損害!!! 有收穫記得回饋,讓我們台灣跨出程式的出頭天...
GaryKao99
中階會員


發表:46
回覆:102
積分:54
註冊:2002-08-23

發送簡訊給我
#5 引用回覆 回覆 發表時間:2004-01-28 10:14:41 IP:218.32.xxx.xxx 未訂閱
哇~~~好神ㄛ    大家看出差異性了嗎
 
int a=5,b=10;
    a^=b^=a^=b;    BCB Compiler:
1.a^=b-------------->(0000 0101 ^ 0000 1010)=0000 1111 (a=15) 
2.b^=(a^=b)--------->(0000 1010 ^ 0000 1111)=0000 0101 (b=5)
3.a^=(b^=(a^=b))---->(0000 1111 ^ 0000 0101)=0000 1010 (a=10)    請看第1行,這裡的a值已經改變了ㄛ(a=15)
所以再帶入第3行的a值已是改變過後的值(a=15)
leobxb大大所說"BCB compiler 會將同一行每一次的變數運算存回變數本身"即是此意    C#/Java Compiler:
1.b^=(a^=b)--------->(0000 1010 ^ 0000 1111)=0000 0101 (b=5)
2.a^=(b^=(a^=b))---->(0000 0101 ^ 0000 0101)=0000 0000 (a=0)    先解釋為何這裡指列出2行呢?
如leobxb大大所說"C# 以及在java 只會將同一行運算完後再存回最終變數"
所以第1行時,b會得到值5;並不像BCB一樣,a值會有改變,這裡的a值仍然是5
而第2行時,因為a值並沒有改變,仍然以值5與b值做xor,所以答案及不是預先所想要的(a=15)    看看計算的步驟        a^=b^=a^=b;
          ---- 步驟一
       ------- 步驟二
    ---------- 步驟三    BCB與Java、C#所計算的步驟是一樣的,那差異性是在哪呢?    BCB compiler 會將同一行每一次的變數運算存回變數本身
而 C# 以及在java 只會將同一行運算完後再存回最終變數
嘿嘿...我只是做個整理...讓自己看懂些 ~~~~~~~~~~~~~~~~~~~~~~ 我什麼都會, 就兩樣不會 就是 這個也不會, 那個也不會
solong
一般會員


發表:1
回覆:3
積分:0
註冊:2003-01-29

發送簡訊給我
#6 引用回覆 回覆 發表時間:2004-01-31 20:33:47 IP:61.70.xxx.xxx 未訂閱
感謝大家的回覆,結論就是leobxb所說的這樣,也感謝GaryKao99的補充,我想分數應該要給leobxb,不過不知道是不是我的主題是開"討論", 所以我看不到給分的的地方! 如果真是這樣,還請
taishyang
站務副站長


發表:377
回覆:5490
積分:4563
註冊:2002-10-08

發送簡訊給我
#7 引用回覆 回覆 發表時間:2004-02-02 03:22:58 IP:61.231.xxx.xxx 未訂閱
solong您好: 您可以參考版規 http://delphi.ktop.com.tw/topic.php?TOPIC_ID=43311 按下鉛筆的圖示即可修改標題改為[問題] 順心
系統時間:2024-05-05 2:43:04
聯絡我們 | Delphi K.Top討論版
本站聲明
1. 本論壇為無營利行為之開放平台,所有文章都是由網友自行張貼,如牽涉到法律糾紛一切與本站無關。
2. 假如網友發表之內容涉及侵權,而損及您的利益,請立即通知版主刪除。
3. 請勿批評中華民國元首及政府或批評各政黨,是藍是綠本站無權干涉,但這裡不是政治性論壇!