【问题标题】:Views or table functions or something else视图或表函数或其他东西
【发布时间】:2009-12-22 20:32:13
【问题描述】:

我设计了 5 个存储过程,它们几乎使用相同的连接条件,但 where 子句中的参数或值在不同的运行中会发生变化。 最好的解决方案是创建一个没有 where 子句的所有连接条件的视图,然后从视图中查询或在视图上工作?如果我创建视图,视图可以自动更新吗? 我可以做子查询或类似的查询(我想我在某处读到的视图不支持子查询,但不是 100% 肯定)

select count(x1) as x1cnt, count(x2) as x2count
from (
        select x1,x2, 
        (
        case when x1 is 'y' then 1 else 0 end +
        case when x2 is 'y' then 1 else 0 end
        ) per
        from vw_viewname) v1
where v1.per = 1

更新如下:

In my queries i use joins similar to this also

select c1,c2,c3
FROM [[join conditions - 5 tables]]
Inner join
(
select x1,x2,x3, some case statements
FROM [[join conditions - 5 tables]]
where t1.s1 = val1 and t2.s2 = v2 etc
) s
on s.id = id

所以我使用了两次连接,所以我想我可以使用一些视图来减少它

【问题讨论】:

    标签: sql sql-server sql-server-2005 stored-procedures views


    【解决方案1】:

    省略 where 子句可能会使查询运行得更慢,或者只是给出比特定查询更多的结果。但是您必须根据您的系统确定这是否有利。

    您将获得可以使用的通用视图结果表。 View 基本上在您使用它们时运行查询,因此您将获得结果,就好像您通过其他机制自己执行查询一样。您可以对视图进行子查询,就像它是另一个表一样。那应该不是问题。但是,如果您有 5 个不同的查询做 5 件特定的事情,那么保留它可能是有益的。其中的一两个可能会被调用更多,而您将使用通用视图表来权衡它们的性能,并且这样做除了视图重用之外没有任何实际收获。

    只有在您从中获得特定好处时,我才会构建视图。

    我也发现了这个post that may be similar不知道你是否觉得它有帮助。

    编辑:嗯,我认为这只会让情况变得更糟。您只需调用视图两次,如果它是通用视图,则意味着每个调用都会得到很多通用结果来处理。

    我想说的是,只需专注于优化这些查询,以准确地为您提供所需的内容。那真的是你有5种不同的程序吗? :)

    【讨论】:

    • 我的 5 个 sps 仅在 where 子句中有所不同,我不断为每个子句添加新条件,是否有最好的方法一次性做到这一点,或者我应该将它们分开
    • 我的经验和理解是视图代入代码;允许优化器在编译引用它的查询时“查看”视图的定义。因此,在视图内部或外部放置 WHERE 子句不会影响性能。 "SELECT * FROM " == "SELECT * FROM WHERE "
    • 好吧,如果它们仅在子句中有所不同,那么您可以查看传入参数进行 proc 调用并在一个存储过程中处理它。但是如果 procA 有 2 个参数,而 procB 有 5 个参数,那么您可能只想让它们保持简单和独立。
    • @Dems 我真的不会怀疑。重复使用相同的视图结果绝对很容易。所以可能根本没有性能受到影响,但我没有看到真正的收益,所以我认为这并不重要。感谢您指出这一点!
    • @Arthur:我能看到的收获是关于维护,其中不带 WHERE 子句的视图定义实现了某种抽象。如果有什么变化,有一个联系点可以更新,从而简化了维护。即使它只是没有 WHERE 子句的 1 个视图和引用该视图的 5 个视图。
    【解决方案2】:

    这是 5 个不同的查询,所以就这样吧。

    将类似的 JOIN 封装在一个视图中是很诱人的,但在不知不觉中,您已经拥有了视图之上的视图和糟糕的性能。我已经看过很多次了。

    “视图中的子查询”可能是指有限制的索引视图。

    【讨论】:

      【解决方案3】:

      除非您谈论索引视图,否则视图实际上会运行脚本以按需生成视图。在这方面,它与使用子查询相同。

      如果我是你,我会保持原样。看起来您应该压缩您的代码(5 个脚本中的每一个都有几乎相同的代码),但这里重要的是不同之处。

      【讨论】:

        【解决方案4】:

        您可以在视图中包含子查询,这种方法是完全可以接受的。

        【讨论】:

          【解决方案5】:

          SQL Server 视图确实支持子查询。而且,从某种意义上说,视图会自动更新自己,因为视图不是持久对象(除非您使用索引视图)。对于非索引视图,每次查询视图时,它都会使用基础表。因此,您的视图将与它们所基于的表一样是最新的。

          在我看来,这里的视图将是一个不错的选择。

          【讨论】:

            【解决方案6】:

            即使它包含一个子选择,也可以创建一个视图。您可以删除视图的位置。

            您确定要在没有分组依据的情况下使用 COUNT 吗?它计算包含非空值或参数的行数。

            【讨论】:

              【解决方案7】:

              我最近做了很多关于查询优化器提供的简化的演示。本质上,如果您对连接进行了足够好的计划,系统可以看到它们是多余的并完全忽略它们。

              http://msmvps.com/blogs/robfarley/archive/2008/11/09/join-simplification-in-sql-server.aspx

              存储过程每次都会做同样的工作(参数有一些影响),但视图(或内联 TVF)将被扩展到外部查询中并简化出来。

              【讨论】:

                猜你喜欢
                • 1970-01-01
                • 1970-01-01
                • 2015-10-05
                • 2016-09-12
                • 1970-01-01
                • 2013-06-01
                • 1970-01-01
                • 1970-01-01
                • 1970-01-01
                相关资源
                最近更新 更多