SQL - CTE 与 VIEW

问题描述 投票:0回答:6

我的问题是

SQL
中的
CTE
View有什么区别。我的意思是在哪种情况下我应该使用
CTE
,哪种情况下应该使用
View
。我知道两者都是某种虚拟表,但我无法区分它们的用途。

我发现了一个类似的问题here,但它与性能有关。

更新1:

例如:我有一个充满交易的数据库(

tbl_trade
)。我需要从 350 万条记录中仅选择当月直到当前时间打开的交易,然后操作数据(在虚拟表上使用不同的查询 - 这看起来像视图)。这里的问题是我想要 3-4 列的
SUM
,然后我需要
SUM
一些列并使用结果创建一个虚拟列(看起来像 CTE)。

例如:

tbl_trade
有列:
profit
bonus
expenses
。 我需要
SUM(profit)
,
SUM(bonus)
,
SUM(expenses)
和一个新列
total
,它将等于
SUM(profit)
+
SUM(bonus)
+
SUM(expenses)

PS。重新运行

SUM
的查询不是一个选项,因为我已经有了结果。

提前致谢!

sql sql-server common-table-expression sql-view
6个回答
53
投票

视图可以被索引,但 CTE 不能。所以这是很重要的一点。

CTE 在

tree hierarchy
i.e. 上表现出色递归

此外,在处理复杂查询时请考虑视图。视图是数据库上的物理对象(但不物理存储数据),可用于多个查询,从而提供灵活性和集中式方法。另一方面,CTE 是临时的,在使用时会创建;这就是为什么它们被称为

inline view

更新

根据您更新的问题,视图将是正确的选择。在 CTE 中处理 350 万行将会给 TempDb 带来额外的开销,最终会降低 SQL Server 的性能。请记住,CTE 是一次性视图,因此不会存储任何统计信息,并且您也无法创建索引。它就像一个子查询。


16
投票

计划优化器对两者的解释完全相同。这只是不同的事情。

视图可以单独使用。它可以将复杂的语句封装为更简单的查询。

CTE 主要用于编写更清晰的代码,例如过程/视图中冗余较少。您也可以使用 CTE 进行递归查询,这是一个非常伟大且强大的功能!

我希望这有助于澄清事情。


12
投票

选择CTE的原因之一:如果要做分层查询,就使用CTE。 CTE 可以递归调用。视图不能递归调用。


5
投票

CTE 仅在查询运行时存在于内存中。查询运行后,CTE被丢弃;除非我们再次定义它,否则它不能用于下一个 SQL 查询。尽管如此,同一个 CTE 可能会在主查询和任何子查询中多次引用。

视图是一个存储的 SQL 查询,每次在另一个查询中引用它时都会执行该查询。请注意,视图不存储特定查询的输出 - 它存储查询本身。

关于 SQL 视图,要记住的关键一点是,与 CTE 相比,视图是数据库中的物理对象,存储在磁盘上。但是,视图仅存储查询,而不存储查询返回的数据。每次您在查询中引用视图时都会计算数据。


1
投票

再添加一项考虑因素:权限。

  • 要创建和使用视图需要
    CREATE
    权限,您可能已被授予也可能未授予这些权限。
  • 如果您已被授予权限,您可能会发现自己与具有类似权限并想要创建或更改具有相同名称的视图的其他人发生命名冲突。
  • 解决命名冲突的最简单方法是创建额外的架构(名称空间)

数据库管理员可能不认同上述内容,因此您可能无法首先创建视图。

在这种情况下,您可以将 CTE 视为一次性视图,它不需要您运行

SELECT
查询所需的更多权限。

我经常使用 CTE 来创建独立且不需要额外维护的东西,尤其是示例代码。


0
投票

目前,文档对

CTE
说得非常清楚:
can be thought of as defining temporary tables that exist just for one query.

参考:https://www.postgresql.org/docs/current/queries-with.html

  1. 如果您在没有 select 语句的情况下运行 CTE,它将抛出如下错误 enter image description here

  2. 取消对CTE的查询语句的注释后,它工作正常 enter image description here

© www.soinside.com 2019 - 2024. All rights reserved.