Sql 我可以在WHERE子句中使用IF语句来确定哪些AND将成为查询的一部分吗?

Sql 我可以在WHERE子句中使用IF语句来确定哪些AND将成为查询的一部分吗?,sql,if-statement,where,Sql,If Statement,Where,我有一个SQL语句,在WHERE cluse中有几个and,我想知道我是否可以在WHERE子句下有一个if THEN ELSE语句来确定执行什么and 将向此查询传递三个参数 WHERE tlv.active = 1 AND tli.active = 1 AND t.endWorkShiftId IS NOT NULL AND t.voidTypeId IS NULL AND tlv.customerId = 1 AND tlv.locationId = 1 AND tlv.dockId =

我有一个SQL语句,在WHERE cluse中有几个and,我想知道我是否可以在WHERE子句下有一个if THEN ELSE语句来确定执行什么and

将向此查询传递三个参数

WHERE  tlv.active = 1
AND tli.active = 1
AND t.endWorkShiftId IS NOT NULL
AND t.voidTypeId IS NULL
AND tlv.customerId = 1
AND tlv.locationId = 1
AND tlv.dockId = 3

IF ( :referenceId IS NULL ) {
    AND tlv.vendorCldcId = :vendCldId
    AND tlv.vendorId = :vendId
}
ELSE {
    AND vru.refId = :referenceId
}

不,没有如果。这种情况也不适用。但您可以使用更复杂的布尔表达式:

WHERE  tlv.active = 1
AND tli.active = 1
AND t.endWorkShiftId IS NOT NULL
AND t.voidTypeId IS NULL
AND tlv.customerId = 1
AND tlv.locationId = 1
AND tlv.dockId = 3
AND (
    (
        :referenceId IS NULL
        AND tlv.vendorCldcId = :vendCldId
        AND tlv.vendorId = :vendId
    ) OR (
        :referenceId IS NOT NULL
        AND vru.refId = :referenceId
    )
)
更新

顺便说一下:这种查询是一种性能反模式。在大多数数据库系统中,复杂表达式会阻止有效的表联接


相反,您应该创建两个独立的、简单得多的查询:一个用于
referenceId为NULL,另一个用于
referenceId为notnull
,并调用其中一个查询。

否,没有IF。这种情况也不适用。但您可以使用更复杂的布尔表达式:

WHERE  tlv.active = 1
AND tli.active = 1
AND t.endWorkShiftId IS NOT NULL
AND t.voidTypeId IS NULL
AND tlv.customerId = 1
AND tlv.locationId = 1
AND tlv.dockId = 3
AND (
    (
        :referenceId IS NULL
        AND tlv.vendorCldcId = :vendCldId
        AND tlv.vendorId = :vendId
    ) OR (
        :referenceId IS NOT NULL
        AND vru.refId = :referenceId
    )
)
更新

顺便说一下:这种查询是一种性能反模式。在大多数数据库系统中,复杂表达式会阻止有效的表联接


与此相反,您应该创建两个独立的、简单得多的查询:
referenceId为NULL
,而
referenceId为notnull
,并调用其中一个或另一个。

否,因为
IF
是命令式语言构造,而SQL查询是根据逻辑谓词定义的(例如,这就是能够自动优化查询执行计划的原因)。因此,您可以实现相同的效果,您只需“功能性地思考”(如在函数式语言中,如Haskell)即可,而且更难确保生成的查询

在您的情况下,您可能需要:

...
AND
tlv.dockId = 3
AND
(
    (
        :referenceId IS NULL
        AND
        tlv.vendorCldcId = :vendCldId
        AND
        tlv.vendorId = :vendId
    )
    OR
    (
        :referenceId IS NOT NULL
        AND
        vru.refId = :referenceId
    )
)
请注意,根据DBMS的不同,这可能会有一个次优的执行计划,因为当查询引擎根据
:referenceId
进行优化时,可能无法消除可选的
条件,尤其是在MSSQL Server的情况下:


…一般的建议似乎是为每一组可能的参数编写单独的查询。

否,因为
IF
是一种命令式语言结构,而SQL查询是根据逻辑谓词定义的(例如,这是实现查询执行计划自动优化的原因)。因此,您可以实现相同的效果,只需“功能性地思考”(如在函数式语言中,如Haskell中),并增加确保结果查询的难度

在您的情况下,您可能需要:

...
AND
tlv.dockId = 3
AND
(
    (
        :referenceId IS NULL
        AND
        tlv.vendorCldcId = :vendCldId
        AND
        tlv.vendorId = :vendId
    )
    OR
    (
        :referenceId IS NOT NULL
        AND
        vru.refId = :referenceId
    )
)
请注意,根据DBMS的不同,这可能会有一个次优的执行计划,因为当查询引擎根据
:referenceId
进行优化时,可能无法消除可选的
条件,尤其是在MSSQL Server的情况下:


…一般的建议似乎是为每个可能的参数集编写单独的查询。

这是哪个dbms???我的错,这是MySQL,我使用HeidiSQL这是哪个dbms???我的错,这是MySQL,我使用HeidiSQL