2

假设有一个存储过程 SetCustomerName,它有一个输入参数 Name,并且我有一个带有列 Name 的表客户。所以在我的存储过程中,我想设置客户的名字。如果我写

UPDATE customers SET Name = Name;

这是不正确的,我必须写(例如)

UPDATE customers SET `Name` = Name;

所以,有一个关于反引号的链接(http://dev.mysql.com/doc/refman/5.0/en/identifiers.html)但是它没有足够深入地解释如何使用它们(如何将它们与参数和列一起使用名称)。

还有一件很奇怪的事情(至少对我来说):你可以用任何一种方式使用反引号:

UPDATE customers SET Name = `Name`;
//or
UPDATE customers SET `Name` = Name;
//or even
UPDATE customers SET `Name` = `Name`;

他们都以完全相同的方式工作。

你不觉得这很奇怪吗?这种奇怪的行为是否在某处得到了解释?

4

1 回答 1

2

我不明白为什么你首先需要使用反引号来逃避。在语句UPDATE x SET a = b中,a必须始终引用x的列。但是b可以是变量或列。鉴于本地范围和变量解析在存储过程中的工作方式b将始终引用本地变量,即使x中存在同名的列。

因此,我无法重现您的问题。我试过这样:

mysql> SELECT * FROM comments;
+----+-----------+---------+
| id | parent_id | content |
+----+-----------+---------+
|  1 |         0 | bar     | 
|  2 |         0 | baz     | 
+----+-----------+---------+
2 rows in set (0.00 sec)
mysql> delimiter //
mysql> CREATE PROCEDURE foo(IN content TEXT)
    -> BEGIN
    ->   UPDATE comments SET content = content;
    -> END //
Query OK, 0 rows affected (0.00 sec)
mysql> delimiter ;
mysql> CALL foo('changed!');
Query OK, 2 rows affected (0.00 sec)
mysql> SELECT * FROM comments;
+----+-----------+----------+
| id | parent_id | content  |
+----+-----------+----------+
|  1 |         0 | changed! | 
|  2 |         0 | changed! | 
+----+-----------+----------+
2 rows in set (0.00 sec)

如您所见,注释表的列内容得到更新,即使内容也是存储过程foo的参数名称。

你确定 UPDATE 客户 SET Name = Name; 给你一个错误?有了上面的解释,似乎合乎逻辑

UPDATE customers SET Name = `Name`;
UPDATE customers SET `Name` = Name;
UPDATE customers SET `Name` = `Name`;

都具有相同的效果。

编辑:当然,SELECT 语句的情况会有所不同。

于 2009-06-03T00:21:21.507 回答