通过视图修改数据
您可以通过视图修改基础基表的数据,其方式与使用 UPDATE、INSERT 和 DELETE 语句,或使用 bcp 实用工具和 BULK INSERT 语句在表中修改数据一样。但是,以下限制应用于更新视图,但不应用于表:
注意: |
---|
下列某些限制不适用于分区视图,且没有任何限制适用于通过 INSTEAD OF 触发器应用的更新。有关详细信息,请参阅本主题后面的“通过视图修改数据的其他选择”。 |
- 任何修改(包括 UPDATE、INSERT 和 DELETE 语句)都只能引用一个基表的列。
- 在视图中修改的列必须直接引用表列中的基础数据。它们不能通过其他方式派生,例如通过:
- 聚合函数(AVG、COUNT、SUM、MIN、MAX、GROUPING、STDEV、STDEVP、VAR 和 VARP)。
- 计算,不能通过表达式并使用列计算出其他列。使用集合运算符(UNION、UNION ALL、CROSSJOIN、EXCEPT 和 INTERSECT)形成的列得出的计算结果不可更新。
- 被修改的列不受 GROUP BY、HAVING 或 DISTINCT 子句的影响。
- 同时指定了 WITH CHECK OPTION 之后,不能在视图的 select_statement 中的任何位置使用 TOP。
上述限制应用于视图的 FROM 子句中的任何子查询,就像其应用于视图本身一样。通常,Microsoft SQL Server 2005 必须能够明确跟踪从视图定义到一个基表的修改。例如,以下视图不可更新:
CREATE VIEW TotalSalesContacts
AS
SELECT C.LastName,
SUM(O.TotalDue) AS TotalSales
FROM Sales.SalesOrderHeader O, Person.Contact C
WHERE C.ContactID = O.ContactID
GROUP BY LastName
不能接受对 TotalSalesContacts
的 LastName
列进行修改,因为该列已受到 GROUP BY
子句的影响。如果同一个姓氏有多个实例,则 SQL Server 将无法知道该更新、插入或删除哪个实例。同样,尝试对 TotalSalesContacts
的 TotalSales
列进行修改将返回错误,因为该列是从聚合函数派生的列。SQL Server 不能直接跟踪该列到其基表 SalesOrderHeader
。
另外还将应用以下附加准则:
- 如果在视图定义中使用了 WITH CHECK OPTION 子句,则所有在视图上执行的数据修改语句都必须符合定义视图的 SELECT 语句中所设置的条件。如果使用了 WITH CHECK OPTION 子句,修改行时需注意不让它们在修改完成后从视图中消失。任何可能导致行消失的修改都会被取消,并显示错误。
- INSERT 语句必须为不允许空值并且没有 DEFAULT 定义的基础表中的所有列指定值。
- 在基础表的列中修改的数据必须符合对这些列的约束,例如为 Null 性、约束及 DEFAULT 定义等。例如,如果要删除一行,则相关表中的所有基础 FOREIGN KEY 约束必须仍然得到满足,删除操作才能成功。
- 不能使用由键集驱动的游标更新分布式分区视图(远程视图)。此项限制可通过在基础表上而不是在视图本身上声明游标得到解决。
- bcp 或 BULK INSERT 和 INSERT ...SELECT * FROM OPENROWSET(BULK...) 语句不支持将数据大容量导入分区视图。但是,您可以使用 INSERT 语句在分区视图中插入多行。有关详细信息,请参阅从视图大容量导出数据或将数据大容量导入视图。
- 不能对视图中的 text、ntext 或 image 列使用 READTEXT 语句和 WRITETEXT 语句。
通过视图修改数据的其他选择
如果本主题的上述限制妨碍直接通过视图修改数据,则可以考虑下列选项:
- 使用具有支持 INSERT、UPDATE 和 DELETE 语句的逻辑的 INSTEAD OF 触发器。有关详细信息,请参阅设计 INSTEAD OF 触发器。
- 使用修改一个或多个成员表的可更新分区视图。有关详细信息,请参阅创建分区视图。
通过视图添加数据
通过视图更改数据
通过视图删除数据
请参阅
概念
帮助和信息
更改历史记录
版本 | 历史记录 |
---|---|
2008 年 11 月 17 日 |
|
2005 年 12 月 5 日 |
|