首页 > 解决方案 > 如何加快不同条件下多次查询同一张表?

问题描述

后台使用EF6、asp mvc core和SQL Server。

我必须对具有不同条件的同一张表进行多次查询,fe

SELECT COUNT(*) FROM Table1 WHERE a = true
SELECT COUNT(*) FROM Table1 WHERE b = true
SELECT COUNT(*) FROM Table1 WHERE a = true || b = true
SELECT a FROM Table1 WHERE b = true

所以4个查询Table1具有不同的条件。我认为因此我必须阅读整个Table1四遍。在伪代码中,它可能看起来像这样。

var res1 = new list();

foreach(var rec in Table1) 
{
    // read Table1 first time
    if(rec.a == true) 
    {
        res1.push(rec);
    }
}

var res2 = new list();

foreach(var rec in Table1) 
{
    // read Table1 second time
    if(rec.b == true) 
    {
        res2.push(rec);
    }
}

var res3 = new list();

foreach(var rec in Table1) 
{
     // read Table1 third time
     if(rec.a == true || rec.b == true) 
     {
         res3.push(rec);
     }
}

var res4 = new list();

foreach(var rec in Table1) 
{ 
    // read Table1 fourth time
    if(rec.b == true) 
    {
        res4.push(rec);
    }
}

我想知道如何Table1仅阅读一次并获得四种不同的结果,如下所示:

var res1 = new List();
var res2 = new List();
var res3 = new List();
var res4 = new list();

foreach(rec in Table1) 
{
     // read Table1 first time
     if(a == true) 
     {
        res1.push(rec);
     } 

     if(b == true) 
     {
        res2.push(rec);
     }

     if(a == true || b == true) 
     {
        res3.push(rec);
     }

     if(b == true) 
     {
        res4.push(rec);
     }  
}  

还有一个挑战,这些查询是动态 sql,我的意思是a = true, b = true,a = true || b = true存储在数据库中。查询以这种方式运行:

string query = "SELECT Count(*) FROM Table1 WHERE" + condition;
var count = ExecuteSql(query);

上面的示例进行了简化,但实际上所有查询都被拆分并存储在数据库中。

PS。实际上我想加快页面速度,向服务器发出 30-40 个请求,每个请求都是对同一张表的查询。我想如果我可以用一个请求而不是 40 个请求来替换它们。

标签: sqlsql-serverentity-frameworkoptimization

解决方案


您可以仅通过单个查询使用条件聚合:

SELECT
    COUNT(CASE WHEN a = true THEN 1 END) AS cnt_a,
    COUNT(CASE WHEN b = true THEN 1 END) AS cnt_b,
    COUNT(CASE WHEN a = true OR b = true THEN 1 END) AS cnt_a_b
FROM Table1;

这会将全表扫描的次数从 3 次减少到仅 1 次。此外,它还可能会将往返数据库的往返次数从 3 次减少到 1 次。


推荐阅读