為什麼編譯器不允許在 Union 使用 std::string?
使用 C 時,通常需要使用資料結構可以儲存不同類型的資料。一種這樣的結構是聯合,它將多個變數分配給同一記憶體位置。然而,出現了一個關於聯合對其成員的限制的常見問題。
一個重要的限制是無法在聯合中包含具有重要複製建構子的類別。這包括像 std::string 這樣的類別。要理解原因,請考慮以下場景:
union U { std::string x; std::vector<int> y; }; U u; // <--
傳統上,在結構體中,初始化 u.x 或 u.y 會將它們設為預設值。然而,在聯合體中,所有成員共享相同的位址,因此不可能在不覆蓋資料的情況下為兩個成員分配值。如果兩個成員都未初始化,則使用它們將導致未定義的行為。
C 98 透過禁止具有非平凡建構子的類別成為聯合成員來解決此問題。具體來說,它在§9.5/1中指出:
「具有非平凡建構子(12.1)、非平凡複製建構子(12.8)、非平凡析構函數(12.4)的類別的對象,或非平凡的複製賦值運算子(13.5.3,12.8)不能是聯合的成員,這樣的陣列也不能物件。
C 0x 在某種程度上放寬了此規則(§9.5/2),最多允許一個非靜態帶有大括號或等號初始值設定項的資料成員。然而,為聯合編寫無錯誤的複製構造函數和析構函數仍然很複雜。因此,標記聯合或第三方函式庫(如 boost::variant 和 boost::any)為處理異質資料提供了替代解決方案。
以上是為什麼不能在 C 聯合中使用 `std::string`?的詳細內容。更多資訊請關注PHP中文網其他相關文章!