天天看點

【Mysql 學習】 MERGE表方面的問題(二)

shell> cd /mysql-data-directory/current-database

shell> ls -1 t1 t2 > total.MRG

shell> mysqladmin flush-tables

要重映射一個MERGE表到一個不同的MyISAM表集,你可以執行下列之一:

·DROP MERGE表并且重建它。

·使用ALTER TABLE tbl_name UNION=(...)來改變底層表的清單。

·改變.MRG檔案,并對MERGE表或者所有底層表發出一個FLUSH TABLE語句來強制存儲引擎去讀新的定義檔案。

MERGE表可以幫你解決以下問題:

·容易地管理一套日志表。比如,你可以把不同月的資料放進分離的表中,用myisampack壓縮其中的一些,并随後建立一個MERGE表來把它們當作一個來使用。

·獲得更快的速度。你可以以一些标準來分割大的隻讀表,然後放進不同磁盤上的單個表中。基于此的一個MERGE表可比使用大表要快得多。

·執行更有效的搜尋。如果你确切知道要搜尋什麼,對一些查詢你可以隻在被分割的表的其中之一來搜尋,并且對其它使用MERGE。你甚至有許多不同的MERGE表,它們使用有重疊的表套。

·執行更有效的修補。修補被映射到一個MERGE表中的單個表比修補單個大型表要更輕松。

·即刻映射許多表成一個。MERGE表不需要維護它自己的索引,因為它使用大哥表的所用。是以,MERGE表集合是非常塊地建立或重映射。(注意,當你建立一個MERGE表之時,即使沒有索引被建立,你必須仍然指定索引定義)。

·如果根據需要或按照批次,你有一組要合起來作為一個大表的表,你應該根據需要對它們建立一個MERGE表來替代大表。這樣要快得多而且節約大量的磁盤空間。

·超過作業系統的檔案尺寸限制。每個MyISAM表都受制于這個限制,但是一個MyISAM表的集合則不然。

·你可以通過定義一個映射到單個表的MERGE表來為一個MyISAM表建立一個别名或“同物異名”。這樣做應該沒有真實的可察覺的性能影響 (對每個讀隻有一些間接調用和memcpy()調用)。

MERGE表的缺點:

·隻能對MERGE表使用僅相同的MyISAM表。

·不能在MERGE表中使用很多MyISAM功能。比如,不能在MERGE表上建立FULLTEXT索引。(可以在底層MERGE 表上建立FULLTEXT索引,但不能用全文搜尋來搜尋MERGE表)。

·如果MERGE表是非臨時的,所有底層MyISAM表也必須是永久的。如果MERGE表是臨時的,MyISAM表可以是任何臨時&非臨時的混合。

·MERGE表使用更多的檔案描述符。如果是個用戶端正使用一個映射到10個表的MERGE表,伺服器使用(10*10)+10個檔案描述符。(10個資料檔案描述符給10個用戶端每人一個,并且在用戶端之間共享10個索引檔案描述符)。

· 鍵讀會更慢。當你讀一個鍵的時候,MERGE存儲引擎需要在所有 底層表上發出一個讀以檢查哪一個接近比對給定的鍵。如果你随後做了一個read-next,MERGE存儲引擎需要搜尋讀緩沖來找出下一個鍵。隻有當一個鍵緩沖被耗盡,存儲引擎才需要讀下一個鍵塊。這使得MERGE鍵在eq_ref搜尋中非常慢,但在ref搜尋中不是太慢。

下列是已知關于MERGE表的問題:

·如果你使用ALTER TABLE 來把MERGE表變為其它表類型,到底層表的映射就被丢失了。取而代之的,來自底層MyISAM表的行被複制到已更換的表中,該表随後被指定新類型。

·REPLACE不起作用。

·沒有WHERE子句,或者在任何被映射到一個打開的MERGE表上的任何一個表上的REPAIR TABLE,TRUNCATE TABLE, OPTIMIZE TABLE或ANALYZE TABLE,你不能使用DROP TABLE, ALTER TABLE, DELETE FROM。如果你這麼做了,MERGE表将仍舊指向原始表,這樣産生意外結果。解決這個不足最簡單的辦法是在執行任何一個這些操作之前發出一個FLUSH TABLES語句來確定沒有MERGE表仍舊保持打開。

·一個MERGE表不能在整個表上維持UNIQUE限制。當你執行一個INSERT, 資料進入第一個或者最後一個MyISAM表(取決于INSERT_METHOD選項的值)。MySQL確定唯一鍵值在那個MyISAM表裡保持唯一,但不是跨集合裡所有的表。

·當你建立一個MERGE表之時,沒有檢查去確定底層表的存在以及有相同的機構。當MERGE表被使用之時,MySQL檢查每個被映射的表的記錄長度是否相等,但這并不十分可靠。如果你從不相似的MyISAM表建立一個MERGE表,你非常有可能撞見奇怪的問題。

·在MERGE表中的索引的順序和它的底層表中的索引應該一樣。如果你使用ALTER TABLE給一個被用在MERGE表中的表添加一個UNIQUE索引,然後使用ALTER TABLE在MERGE表上添加一個非唯一索引,如果在底層表上已經有一個非唯一索引,對表的索引排序是不同的。(這是因為ALTER TABLE把UNIQUE索引放在非唯一索引之前以利于重複鍵的快速檢測 )。是以對使用這樣索引的表的查詢可能傳回不期望的結果。

·在Windows中,在一個被MERGE表使用的表上DROP TABLE不起作用,因為MERGE引擎的表映射對MySQL的更上層隐藏。因為Windows不允許已打開檔案的删除,你首先必須重新整理所有MERGE表(使用FLUSH TABLES)或在移除該表之前移除MERGE表。

繼續閱讀