1

我目前正在阅读一本书,使用 Microsoft SQL Server 2012,第三版交付商业智能。在本书中,它有一个部分说明了以下内容:

数据集市的特点

因为数据集市旨在用作商业智能的来源,而不是管理组织的日常事务,所以它的设计与 OLTP 数据库不同。数据集市不是围绕规范化规则构建的,而是为了访问速度而构建的。数据集市仍然是一个关系数据库,但它的设计目的是在输出数据以进行分析和报告时需要更少的表连接。在数据集市中,为了速度,可以重复数据(非规范化)。

在设计数据集市时,规范化规则被围绕“事实”组织的不同设计方法所取代。这些新的设计方法被称为星星和雪花。我们在“星形模式”和“雪花模式”部分讨论星形和雪花。星星和雪花可能看起来像是孩子们的幻想,但实际上,它们提供了相当成熟和脚踏实地的方法来创建快速且易于访问的信息。

多么棒的信息啊!但这就是混乱开始的地方。我知道 SQL Server 允许使用存储过程作为优化查询性能的一种方式。虽然我不知道这些的内部工作原理,但我知道服务器具有优化查询性能的内置方法,可以在传统的规范化数据库中快速运行查询。例如,假设我有一个 Sales 表,其中列出了 20,000 行,这些行都是已售出的单个产品。如果我想知道这些行的总和,我可能会将查询保存SELECT SUM(SALES.SALESPRICE) FROM SALES在存储过程中。

如果我知道存储过程是预编译的,那么服务器不会自动知道它必须在每次插入完成时获取这个总和并缓存查询结果吗?那么,每当添加第 20,001 行时,就会自动保存销售金额,因此上述存储过程的结果立即可用?这不就是执行计划背后的全部想法吗?还是我完全错过了“优化”查询的功能?

如果不是这种情况,我将不胜感激了解存储过程的内部工作原理,以及与从 SQL Server Management Studio (SSMS) 进行直接查询相比,它如何产生性能优势

谢谢!!!!

4

3 回答 3

2

是的,恐怕你错过了重点。

存储过程的一个好处是计算如何获取结果而不是计算结果也需要处理时间——存储过程缓存的正是这一点execution plan

http://www.simple-talk.com/sql/performance/execution-plan-basics/

也许存储过程的更大好处在于能够更精细地保护对您的数据的访问,并在不更改外部(SP)接口的情况下隐藏或更改您的架构 - 即:我可以阻止任何用户发出INSERT,UPDATEDELETE针对我的命令数据,仅允许他们访问执行类似任务或多项任务的某些程序。

如果您确实想存储总和计算的结果,则可以这样做,但它必须位于专用表中,或者如果要对总和进行分组,则它必须位于现有表中的附加字段中 - 并且计算必须手动编写 - 在INSERT,UPDATEDELETE事件上的触发器中,或者通过您为执行这些数据操作功能而编写的存储过程中的附加代码 - 所以现在您的存储过程读取类似

create proc SellProduct (@productID int, @price money)
as
begin
    insert ProductSales (ProductID, SalePrice) values (@productID, @price)
    update Products set TotalSales = TotalSales + @price WHERE productid = @productID
end

(您可能想在完成上述代码之前阅读有关事务的信息)

于 2012-09-06T08:12:32.610 回答
1

所以,我删除了 MDX 标记,因为您的问题是关于存储过程的,您只是使用 olap 来举例说明您的问题。

因此,当您说存储过程是预编译的时,请记住这不适用于过程的结果。如果你有一个带有 select(sum) 的过程,每次你运行它时,select(sum) 都会被提交到数据库中。结果不会存储在任何地方。

您提到了性能优势。将查询包装在过程中不会带来任何性能优势。在幕后,无论查询是否在 proc 内,查询都将准确执行。程序的好处更多地与 waht @podiluska 说。

我认为您的主要困惑(基于您所写的这一行:)Whenever line 20,001 is added, the amount of the sale would automatically be saved so the result of the above stored procedure是您认为程序是包含数据的对象,而事实并非如此。过程、视图(非持久性)和函数是您用来更好地查询或数据的机制

于 2012-09-06T08:23:54.667 回答
1

OLAP 将一百万个不同 SUM 的结果存储在您的数据集市中。OLTP(“普通”SQL 数据库)仅存储基础数据,并在您调用存储过程时计算 SUM。

存储过程被编译,就像 C 程序一样。您在过程之外编写的 SQL 查询在运行时被翻译,就像 ASP 网页一样。两者都不包含数据。

于 2012-09-11T21:19:44.947 回答