我有一个表,其中包含对查看我的应用程序的用户没用的部分数据。观众希望看到一个类似的表,其中包含所有计算出的值,并且希望能够快速查询该数据。通常,这将是使用View的理想场所。不幸的是,计算的复杂性限制了我对Views的使用,所以我需要一个替代解决方案。我正在考虑做以下事情......
表A包含后端数据。每次更新此表时,触发的触发器都会更新表B,其中显示了这些计算的结果。此时可以快速查询表B.
我唯一担心的是计算过程有点冗长,表A有可能在突发中多次更新。有没有像“之前选择”触发器那样的解决方案?所以基本上表A可以连续多次更新,但只有在查询表B时才会进行计算?
以下是一个示例时间表:
所以我的问题是:
感谢任何解决方案/见解!
编辑 - 关于为什么(我认为至少)触发器实现缓慢的更多细节:
答案 0 :(得分:2)
触发器对插入或更新的整批记录进行操作,而不是一次一行。
如果计算花费的时间太长而只有几百条新记录,那么计算本身可能需要进行性能调整。
如果你在触发器中进行计算,那么它们就是每个事务的一部分,并且它们将在允许另一个事务之前完成,因此可以想象它会减慢插入速度。如果你正确地编写了触发器来处理数据集而不是逐行激动,那么它可能不会引起问题。数百行是完成大多数计算的微不足道的数量。如果您批量插入数百万行,我会更关注触发性能干扰其他进程。
您可以创建一个proc来进行计算并将其安排为每十分钟左右运行一次,然后在调用报告时再次运行。通过这种方式,它可以提前进行大部分预先计算,并在报告时捕获最后几个新记录。
给我们一个计算样本和潜在触发器,我们可以更好地帮助您。
如果单个事务进入一个组触发器运行,则无法对一组进行分组。也许你应该停止使用LINQ,如果你需要批量处理,你可以发送一个abatch stament。如果您一次使用多个记录,通常最好使用基于集合的操作。
答案 1 :(得分:2)
我认为物化视图能够解决这个问题,并且运行得相当快。然而,OP没有说出“计算”是什么,只是说它们运行缓慢。因此,这是您最好的选择:
在主表A中添加一个触发器,在该触发器中将受影响行的ID插入到新的“需要完成的工作”表中。由于计算尚未完成,因此开销非常低。
创建一个每x分钟运行一次的作业来进行工作计算并清除“需要完成的工作”表。这项工作将填充并保持与表B保持同步,表B具有最终答案。
仅通过存储过程调用访问“查询”,在此过程中,运行作业使用的处理(将确保表B中的数据是最新的)然后它将使用表B.
答案 2 :(得分:0)
如果可能(当然可能不在您的特定情况下),您可以通过存储过程调用从表B返回数据,而不是从视图/表中选择。这样,只有在专门调用时(即表A已更新后),您的程序才会执行繁重的工作。
答案 3 :(得分:0)
这是对已经讨论过的更简单的变化......
如果您在两个表上都有DeltaTs / EditTs列,则可以:
通过存储过程返回查询数据,该存储过程将检查两个表上的max(Deltats)vs max(deltats)并根据需要更新表b。在更新表A后第一次选择时,你会受到一些打击,但之后它会很好而且很快。