简体   繁体   English

SQL在where子句中优化条件

[英]SQL optimise conditions in where clause

In asp I have setup several dropdowns which allow the user to filter down the data displayed on the page based on their selection. 在asp中,我设置了几个下拉菜单,允许用户根据自己的选择过滤显示在页面上的数据。

These dropdowns are for a Data Collection, a year group eg Year 11, a subject eg English, a teaching group and a subgroup. 这些下拉列表用于数据收集,年份组(例如11年级),学科(例如英语),教学组和子组。

The Data Collection, Year and Subject must all be selected, but the teaching group and subgroup can remain unselected (select all), selected individually or both selected. 必须全部选择“数据收集”,“年份”和“科目”,但是教学组和子组可以保持未选中状态(全部选中),单独选择或同时选中。

My where clause in an SQL stored procedure is now huge because of the many options under subgroup. 由于子组下有许多选项,因此SQL存储过程中的where子句现在非常庞大。 Below are a couple of options where no subgroup is selected or the subgroup of Girls is selected or the subgroup of Boys is selected. 以下是几个选项,其中没有选择任何子组,或者选择了“女孩”的子组,或者选择了“男孩”的子组。 There are many more than this, but for the sake of brevity I've limited what I've posted. 还有很多,但是为了简洁起见,我限制了我发布的内容。

My question is can I optimise this code in any way or am I at its most concise? 我的问题是我可以以任何方式优化此代码,还是最简洁? If you need more examples let me know and I'll add them to the post. 如果您需要更多示例,请告诉我,我将其添加到帖子中。

where 

--All
(@TeachingGroup = 'Select All' AND ([StuYear] = @StuYear) AND ([DataCollection] = @DataCollection) AND ([Name] = @SubjectName)  AND @Subgroup='Select All'
OR 
@TeachingGroup <> 'Select All' AND ([StuYear] = @StuYear) AND ([DataCollection] = @DataCollection) AND ([Name] = @SubjectName) AND ([TeachingGroup] = @TeachingGroup)  AND @Subgroup='Select All')
or
--Gender Girls
(@TeachingGroup = 'Select All' AND ([StuYear] = @StuYear) AND ([DataCollection] = @DataCollection) AND ([Name] = @SubjectName)  AND Gender = 
case when @Subgroup = 'GenF' then 'F' end)
OR 
@TeachingGroup <> 'Select All' AND ([StuYear] = @StuYear) AND ([DataCollection] = @DataCollection) AND ([Name] = @SubjectName) AND ([TeachingGroup] = @TeachingGroup)  AND Gender = case when @Subgroup = 'GenF' then 'F' end
or
--Gender boys
(@TeachingGroup = 'Select All' AND ([StuYear] = @StuYear) AND ([DataCollection] = @DataCollection) AND ([Name] = @SubjectName)  AND Gender = 
case when @Subgroup = 'GenM' then 'M' end)
OR 
@TeachingGroup <> 'Select All' AND ([StuYear] = @StuYear) AND ([DataCollection] = @DataCollection) AND ([Name] = @SubjectName) AND ([TeachingGroup] = @TeachingGroup)  AND Gender = case when @Subgroup = 'GenM' then 'M' end

If you get many more criteria, you'll probably want to investigate dynamic SQL, where you build different queries depending on what is supplied. 如果您获得更多的条件,则可能需要研究动态SQL,根据提供的内容构建不同的查询。

Also, it would be fairly standard practice to pass 'Null' to mean 'Select All' 此外,将“ Null”传递为“ Select All”将是相当标准的做法

However, this is a simpler version of what you have: 但是,这是您所拥有的一个简单版本:

Where
    [StuYear] = @StuYear And
    [DataCollection] = @DataCollection And
    [Name] = @SubjectName And (
        @TeachingGroup = 'Select All' Or 
        [TeachingGroup] = @TeachingGroup
    ) And (
       @SubGroup = 'Select All' Or
       Gender = Case 
               When @SubGroup = 'GenF' Then 'F'
               When @SubGroup = 'GenM' Then 'M'
           End
    )

Dynamic sql example 动态SQL示例

Declare 
    @params nvarchar(max) = '
@StuYear int,
@DataCollection varchar(30),
@SubjectName varchar(30),
@TeachingGroup varchar(30),
@SubGroup varchar(30)', --replace with your definitions
    @sql nvarchar(max) = '
Select 
    xxx 
from 
    xxx 
Where
    [StuYear] = @StuYear And
    [DataCollection] = @DataCollection And
    [Name] = @SubjectName'

If @TeachingGroup != 'Select All'
   Set @sql += ' And TeachingGroup = @TeachingGroup'

If @SubGroup != 'Select All'
   Set @sql += ' And Gender = Right(@SubGroup, 1)'

Exec sp_executesql @sql, @params, 
    @StuYear, @DataCollection, @SubjectName, @TeachingGroup, @SubGroup

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM