我试图在同一表中更新来自用户名和姓的电子邮件地址值。
生成的邮件模式:<Firstname>.<Lastname>@test.org
示例表" Persons ":
Firstname Lastname email
Henley Figueroa none@none.com
Samina Morrison none@none.com
Dev Rowe none@none.com
表" Persons "的期望结果:
Firstname Lastname email
Henley Figueroa Henley.Figueroa@test.org
Samina Morrison Samina.Morrison@test.org
Dev Rowe Dev.Rowe@test.org
SQL代码
UPDATE Persons
SET
email = (SELECT FirstName || "." || LastName ||"@"||"test.org" FROM Persons)
person表的实际结果:
Firstname Lastname email
Henley Figueroa Henley.Figueroa@test.org
Samina Morrison Henley.Figueroa@test.org
Dev Rowe Henley.Figueroa@test.org
只有返回结果表的第一个记录被反复使用。为什么?
如果我提交了SELECT:UPDATE Persons
SET
email = FirstName || "." || LastName ||"@"||"test.org"
我得到了预期的结果。
参考你的回答,我用两个表格的例子来扩展我的问题。一个只有名字,另一个有邮件地址。表人:
您找到了解决问题的正确语法。所以问题是为什么这不是你想要的?
UPDATE Persons
SET email = (SELECT FirstName || "." || LastName ||"@"||"test.org"
FROM Persons
);
事实上,这个在任何SQL引擎中都应该产生一个错误——尽管SQLite对这种错误可能有点松懈。为什么?SET
期望一个单个值。这段代码有一个返回三个值的子查询。
注意:SQL Fiddle显示SQLite接受这种语法。Argggh !您可以将其切换到Postgres以查看错误。通过一些修改,对于创建代码,您也可以使用SQL Server或Oracle或几乎任何数据库看到相同的错误(子查询返回多行)。
显然,SQLite只是随意地选择了其中一个值——它第一次遇到的那个值。对于所有三行,这是相同的值。
您已经知道这里的子查询是不正确的。你的问题中的代码是正确的。
From子查询表达式:
用括号括起来的SELECT语句是子查询。所有类型的SELECT语句,包括聚合和复合SELECT查询(带有UNION或EXCEPT等关键字的查询)允许作为标量子查询。子查询表达式的值为包含的SELECT语句的结果。a的值如果所包含的SELECT语句返回,子查询表达式为NULL没有行。
子查询得到的值是返回行的第一行。当然,您不需要SELECT
语句。
这是一个简单的UPDATE
语句,仅涉及当前行的列值:
UPDATE Persons
SET email = FirstName || '.' || LastName || '@' || 'test.org'
Results: