根据函数规范排除 where 子句

Exclude where clause based on function specification

我开发了以下功能:

create function kv_fn_ValuationPerItem_AW (@dDate date, @active bit)
returns table
as

return
(
select
    Code                                                    ItemCode
,   Description_1                                           ItemDescription
,   ItemGroup
,   Qty_On_Hand                                             CurrentQtyOnHand
,   AveUCst                                                 CurrentAvgCost
,   Qty_On_Hand*AveUCst                                     CurrentValue

from        _bvSTTransactionsFull   t
inner join  StkItem                 s   on  t.AccountLink = s.StockLink
where       ServiceItem = 0
and         ItemActive = @active
and         TxDate  <=  @dDate
group by    Code,   Description_1,  ItemGroup,  Qty_On_Hand,    AveUCst
)

该函数需要两个参数:

  1. 日期
  2. 商品是否有效 - 1 = 有效 & 0 = 无效

如果我使用上面规定的功能,通过为活动参数指定 1,那么结果将只针对活动项目。

如果我指定 0,那么它将 return 所有非活动项目。

如何更改此功能以适应活动项目或活动项目和非活动项目?

即如果参数为 1,where 子句应读作 ItemActive = @active,但当参数为 0 时,where 子句应读作 ItemActive in (1,0), 如何更改函数以这样工作?

我尝试了一个案例,但是我的语法不正确...

这就像在您的 where 子句中添加一个 or 一样简单:

...

and         (ItemActive = 1 OR @active = 0)

...

顺便说一句,您可能想这样做:

and         (ItemActive = @active OR @active IS NULL)

这意味着当您将 1 作为 @active 传递时,您将仅获得活跃的项目,当您传入 0 时,您将仅获得非活跃的成员,但是当您传入 null 时,您将获得所有记录,而不管 ItemActive 列中的值如何。

我想你正在寻找这个:

DECLARE @mockup TABLE(ID INT IDENTITY,SomeValue VARCHAR(100),Active BIT);
INSERT INTO @mockup VALUES('Row 1 is active',1)
                         ,('Row 2 is active',1)
                         ,('Row 3 is inactive',0)
                         ,('Row 4 is inactive',0);

DECLARE @OnlyActive BIT=0; --set this to 1 to see active rows only

SELECT *
FROM @mockup m
WHERE (@OnlyActive=0 OR m.Active=1);

想法是:如果参数设置为 0,则此表达式始终为真,否则,列 Active 必须设置为 1。

提示:我使用了括号,在这个简单的例子中不需要它。但是在您更复杂的 WHERE 子句中,将需要它们...

提示 2: 我将参数命名为 OnlyActive,它更好地表达了您要查找的内容。您也可以使用反逻辑将参数转换为 ShowAll...

感谢 Shnugo 和 Zohar 的回答,

请修改您的答案,然后我会将您的答案标记为答案。

我的问题的解决方案是按如下方式更改函数:

create function kv_fn_ValuationPerItem_AW (@dDate date, @active bit)
returns table
as

return
(
select
    Code                                                    ItemCode
,   Description_1                                           ItemDescription
,   ItemGroup
,   Qty_On_Hand                                             CurrentQtyOnHand
,   AveUCst                                                 CurrentAvgCost
,   Qty_On_Hand*AveUCst                                     CurrentValue

from        _bvSTTransactionsFull   t
inner join  StkItem                 s   on  t.AccountLink = s.StockLink
where       ServiceItem = 0
and         ItemActive in (1,@active)
and         TxDate  <=  @dDate
group by    Code,   Description_1,  ItemGroup,  Qty_On_Hand,    AveUCst
)