MySQL replace語句
MySQL replace語法
REPLACE [LOW_PRIORITY | DELAYED] [INTO] tbl_name [PARTITION (partition_name [, partition_name] ...)] [(col_name [, col_name] ...)] {VALUES | VALUE} (value_list) [, (value_list)] ... REPLACE [LOW_PRIORITY | DELAYED] [INTO] tbl_name [PARTITION (partition_name [, partition_name] ...)] SET assignment_list REPLACE [LOW_PRIORITY | DELAYED] [INTO] tbl_name [PARTITION (partition_name [, partition_name] ...)] [(col_name [, col_name] ...)] SELECT ... value: {expr | DEFAULT} value_list: value [, value] ... assignment: col_name = value assignment_list: assignment [, assignment] ...
REPLACE的工作方式與INSERT完全相同,不同的是,如果表中的舊行與PRIMARY KEY或UNIQUE索引中的新行具有相同的值,則在插入新行之前刪除舊行。
REPLACE是MySQL對SQL標準的擴充套件。它要麼插入,要麼刪除和插入。
DELAYED插入和替換在MySQL 5.6中已被棄用。MySQL 5.7不支援DELAYED。伺服器識別但忽略DELAYED關鍵字,將替換作為非延遲替換處理,並生成er_warn_legacy_syntax_convert警告。(不再支援REPLACE DELAYED。語句被轉換為REPLACE。)DELAYED關鍵字將在未來的版本中被刪除。
只有當一個表有一個主鍵或唯一索引時,REPLACE才有意義。否則,它將等價於INSERT,因為沒有索引可用於確定新行是否與另一行重複。
所有列的值都取自REPLACE語句中指定的值。所有缺失的列都被設定為預設值,就像INSERT一樣。不能引用當前行的值並在新行中使用它們。如果使用諸如SET col_name = col_name + 1這樣的賦值,對右邊列名的引用將被視為DEFAULT(col_name),因此賦值等價於
SET col_name = DEFAULT(col_name) + 1。
要使用REPLACE,必須同時擁有表的INSERT和DELETE特權。
如果顯式替換生成的列,則唯一允許的值是DEFAULT
REPLACE支援顯式分割槽選擇,使用partition關鍵字和分割槽、子分割槽或兩者的相對名稱列表。與INSERT一樣,如果不可能將新行插入到任何這些分割槽或子分割槽中,則REPLACE語句將失敗,並出現Found a row not matching the given partition set錯誤。
REPLACE語句返回一個計數,以指示受影響的行數。這是刪除和插入的行之和。如果對於單行REPLACE計數為1,則插入一行,不刪除任何行。如果計數大於1,則在插入新行之前刪除一個或多箇舊行。如果表包含多個唯一索引,並且新行在不同唯一索引中重複不同舊行的值,則單個行可以替換多箇舊行。
受影響的行數可以很容易地確定REPLACE是隻新增了一行,還是也替換了任何行:檢查計數是否為1(新增)或更大(替換)。
如果您使用的是C API,受影響的行數可以透過mysql_affected_rows()函式獲得。
您不能在子查詢中替換一個表並從同一表中進行選擇
MySQL對於replace(和load data ... replace)使用如下演算法:
1.嘗試將新行插入到表中
2.當因為主鍵或唯一索引出現重複鍵錯誤而插入失敗時:
a.從表中刪除具有重複鍵值的衝突行
b.請再次將新行插入表中
在出現重複鍵錯誤的情況下,儲存引擎可能會將REPLACE作為更新而不是刪除加插入來執行,但語義是相同的。除了儲存引擎增加Handler_xxx狀態變數的方式不同之外,沒有使用者可見的影響
因為REPLACE …SELECT語句的結果依賴於SELECT語句中的行順序,並且這種順序不能總是得到保證,當記錄這些語句時,主伺服器和從伺服器可能出現分歧。基於這個理由,replace ... select語句對於基於語句的複製來說被標記為不安全。當使用基於語句的模式時,這些語句會在錯誤日誌中產生一個警告,而當使用MIXED模式時,這些語句會使用基於行的格式寫入二進位制日誌。
當修改沒有分割槽的現有表以適應分割槽時,或者在修改已分割槽表的分割槽時,可以考慮修改表的主鍵(參見22.6.1節,分割槽鍵、主鍵和唯一鍵)。您應該注意,如果這樣做,REPLACE語句的結果可能會受到影響,就像修改非分割槽表的主鍵一樣。考慮下面的CREATE table語句建立的表:
CREATE TABLE test ( id INT UNSIGNED NOT NULL AUTO_INCREMENT, data VARCHAR(64) DEFAULT NULL, ts TIMESTAMP NOT NULL DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP, PRIMARY KEY (id) );
當我們建立這個表並執行mysql客戶機中顯示的語句時,結果如下所示:
mysql> REPLACE INTO test VALUES (1, 'Old', '2014-08-20 18:47:00'); Query OK, 1 row affected (0.03 sec) mysql> REPLACE INTO test VALUES (1, 'New', '2014-08-20 18:47:42'); Query OK, 2 rows affected (0.10 sec) mysql> SELECT * FROM test; +----+------+---------------------+ | id | data | ts | +----+------+---------------------+ | 1 | New | 2014-08-20 18:47:42 | +----+------+---------------------+ 1 row in set (0.01 sec)
現在我們建立第二個表,與第一個表幾乎相同,除了主鍵現在是包含2列的複合主鍵,如下所示(強調文字):
CREATE TABLE test2 ( id INT UNSIGNED NOT NULL AUTO_INCREMENT, data VARCHAR(64) DEFAULT NULL, ts TIMESTAMP NOT NULL DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP, PRIMARY KEY (id, ts) );
當我們在test2上執行與在原始測試表上相同的兩個REPLACE語句時,我們得到了不同的結果:
mysql> REPLACE INTO test2 VALUES (1, 'Old', '2014-08-20 18:47:00'); Query OK, 1 row affected (0.06 sec) mysql> REPLACE INTO test2 VALUES (1, 'New', '2014-08-20 18:47:42'); Query OK, 1 row affected (0.01 sec) mysql> SELECT * FROM test2; +----+------+---------------------+ | id | data | ts | +----+------+---------------------+ | 1 | Old | 2014-08-20 18:47:00 | | 1 | New | 2014-08-20 18:47:42 | +----+------+---------------------+ 2 rows in set (0.01 sec)
這是因為,當執行test2時,id和ts列值必須與現有行的值匹配,以便替換該行;否則,插入一行。
使用MyISAM等儲存引擎(使用表級鎖)的REPLACE語句影響分割槽表,只要不更新表分割槽列,則只鎖那些包含匹配REPLACE語句WHERE子句的行的分割槽;否則鎖定整個表。(對於像InnoDB這樣使用行級鎖的儲存引擎,不會發生分割槽鎖。)
來自 “ ITPUB部落格 ” ,連結:http://blog.itpub.net/26015009/viewspace-2848572/,如需轉載,請註明出處,否則將追究法律責任。
相關文章
- mysql語句MySql
- mySql常用語句MySql
- MySQL的語句MySql
- 【MySQL】MySQL語句最佳化MySql
- mysql查詢語句MySql
- Mysql日期常用語句MySql
- MySQL基礎語句MySql
- Mysql小白語句整理MySql
- 【MySQL】常用拼接語句MySql
- mysql的常用語句MySql
- MySQL迴圈語句MySql
- 初識mysql語句MySql
- Mysql之查詢語句MySql
- Mysql中的DQL語句MySql
- MySQL 三種新增語句MySql
- MySQL 四種新增語句MySql
- mysql handler語句之一MySql
- mysql查詢語句集MySql
- MySQL——優化ORDER BY語句MySql優化
- MYSQL SQL語句優化MySql優化
- mySQL中replace的用法MySql
- MYSQL中replace into的用法MySql
- mysql 語句如何最佳化MySql
- MySQL之SQL語句優化MySql優化
- MySQL 的 EXPLAIN 語句及用法MySqlAI
- mysql建立外來鍵語句MySql
- 入門MySQL——DML語句篇MySql
- mysql高階查詢語句MySql
- mysql 常用sql語句 簡介MySql
- 手擼Mysql原生語句--多表MySql
- MySQL中常用的SQL語句MySql
- MySQL基礎之DML語句MySql
- MySQL的update語句避坑MySql
- MySQL基本操作語句小結MySql
- MySQL中explain語句的使用MySqlAI
- MySQL基本sql語句總結MySql
- MySQL -update語句流程總結MySql
- MySQL檢視建表語句MySql