posts - 8,  comments - 6,  trackbacks - 0

          1.10  “==”不等于“.equals”

          這里舉出一個Java編程程序員經常碰到的問題。例如現在是凌晨3點,在你喝完第4杯咖啡后,你設法找到正確的邏輯來解決復雜的編程問題。到目前,你幾乎不能思考String和Object引用,因為你已經昏昏欲睡了。然后糟糕的事情發生了……不,并不是Java溢出,而是如下所示。

          String name = getName();
          if (name == "Sleepy") // oops!
          {
          doSomething();
          }

          你快速編譯并測試代碼后,代碼似乎正常運行。終于到下班回家休息的時候了!然而,一段時間后,應用程序測試發現了一個間歇性錯誤,并跟蹤到此錯誤的來源恰好是這段代碼。

          “怎么會這樣?”你可能會憤怒地說,“前幾天我還試驗過類似的String比較,并且能夠正確運行!”。但是,你需要首先重溫一下Java對象引用的概念。一個對象變量是一個指向存儲在堆內存(heap memory)中實際對象的引用(指針)。當為另一個變量分配一個變量時,事實上分配的是引用而不是實際的對象(如圖1-1所示):

          String a, b, c, d;
          a = "123";
          b = a;
          c = new String("123");
          d = "WCJ";

          圖 1-1  對象引用

          Java中,“==”運算符用來比較兩個引用以查看它們是否指向同一個內存對象。而對于String實例,運行時狀態會盡可能地確保任意兩個具有相同字符信息的String字面值指向同一個內部對象。此過程稱為駐留(interning),但是它并不有助于每個String的比較。一個原因是垃圾收集器線程刪除了駐留值,另一個原因是String所在的位置可能被一個由String構造函數創建的新實例占用。如果是這樣,“==”將總是返回false。
          可以設計equals方法來比較兩個對象的狀態(state)或每個對象的內容。對你自己的類,必須重寫此方法來使它正確操作。但是如果使用equals方法,String實例總是能夠正確地比較。假定所有的String值是駐留的,下面的代碼段說明了此問題:

          String name1, name2, name3;
          name1 = "123";

          name2 = name1;
          if (name1 == name2) {}         // true
          if (name1.equals(name2)) {}    // true

          name2 = "123";
          if (name1 == name2) {}         // usually true
          if (name1.equals(name2)) {}    // true

          name3 = new String("123");
          if (name1 == name3) {}         // false
          if (name1.equals(name3)) {}    // true


          注意:

          總是使用.equals來比較兩個String值,盡管使用“==”運算符看似能夠正確操作。對于大多數應用程序而言,即使它能正確運行,但“==”代碼事實上是錯誤的,而只有equals是正確的。因此告訴所有你的開發同行支持String的“equals(平等)”權吧(這很可能是本書中最差的雙關語)!


          <2025年8月>
          272829303112
          3456789
          10111213141516
          17181920212223
          24252627282930
          31123456

          留言簿(1)

          隨筆分類

          隨筆檔案

          文章分類

          文章檔案

          搜索

          •  

          最新評論

          閱讀排行榜

          主站蜘蛛池模板: 清丰县| 衡阳县| 哈密市| 穆棱市| 桂平市| 平果县| 秦皇岛市| 沙河市| 蓬溪县| 长治市| 罗定市| 伊宁市| 磐安县| 阳东县| 宁南县| 施秉县| 珲春市| 孟津县| 张家港市| 辉县市| 文安县| 临西县| 酉阳| 云阳县| 株洲县| 吉水县| 甘孜| 田林县| 闻喜县| 紫金县| 天台县| 府谷县| 胶州市| 盈江县| 乐清市| 高安市| 贵阳市| 云龙县| SHOW| 辽中县| 横峰县|