你能在CASE语句中使用随机数吗?(SQL Server 2016)

5

我尝试构建一个适用于较大SELECT语句的CASE语句。我希望每一行都可以单独解析(使用不同的随机数),但在评估特定行内的CASE语句时,随机数是相同的,如果这有意义的话。

我已经尝试过了。

    SELECT 
    [Player name]
    ,[Stake]
    ,[current jackpot]

         ,CASE

         WHEN 
         rand() < 0.23
         THEN
         'Win'
         WHEN
         rand() BETWEEN 0.23 AND 0.89
         then
         'Lose'
         when
         rand() >= 0.89
         then
         'Jackpot'
         else
         'other'
         end as [outcome]
...

但是有时候我会得到一个“其他”结果,这表明每个WHEN语句正在创建一个不同的随机数进行评估。我也不能在开头声明一个全局随机数并使用它,因为每行应该单独解决。


1
你可以声明一个变量并保存 rand() 函数的值,然后在查询中使用它。 - TheGameiswar
2
上述的重复并不是真正的重复。在这种情况下,OP在SELECT中多次引用相同的随机数。这会产生差异。 - Gordon Linoff
选择 当 rand_value < 0.23 时的情况,然后从 (select rand() as rand_value) 中选择...... - ventik
案例_expression_,不是_statement_。 - jarlh
据我所知,只有在使用rand_value进行计算时才会出现不同的值,而且只有这些计算的结果可能会有所不同。如果您比较纯rand_values,它们将是相同的。 - ventik
显示剩余5条评论
3个回答

4

你可以。然而,rand() 仅在每个查询中被计算一次,而不是每行一次。相反,你需要对 newid() 进行操作。但是,因为你在 CASE 中多次引用该值,这就带来了一个挑战。一种方法是:

SELECT . . .
        (CASE WHEN rnd < 0.23 THEN 'Win'
              WHEN rnd < 0.89 THEN 'Lose'
              WHEN rnd >= 0.89 THEN 'Jackpot'
              ELSE 'Other' -- impossible
         END) as [outcome]
FROM (SELECT t.*, rand(convert(varbinary, newid())) as rnd
      FROM t
     ) t

2
我认为你的意思是"rand()不是每行只计算一次",否则原始查询就可以工作。 - D Stanley
@DStanley,我是指“每个查询只执行一次”。谢谢你的解释。 - Gordon Linoff

0
每次调用RAND()时,都会给出一个随机种子,因为您没有指定。只需给RAND()一个种子,它就会保持不变。
select 
    case when 1 = 1 then rand(4) end
    ,case when 2=2 then rand(4) end

或者使用列值...

select 
    case when 1 = 1 then rand(someColumn) end
    ,case when 2=2 then rand(someColumn) end

这难道不意味着每一行都有相同的结果吗? - tomdemaine
是的,如果您提供一个种子;否则,如果您使用的列对行是唯一的。 - S3S

0
另一个选项是使用Cross Apply

示例

Select [Player name]
      ,[Stake]
      ,[current jackpot]
      ,[OutCome] = case when b.randV<0.23 then 'win'
                        when b.randV between 0.23 and 0.89 then 'lose'
                        when b.randV>=0.89 then 'Jackpot'
                        else 'other' end
 From  YourTable
 Cross Apply (values (rand(cast( NewID() as varbinary )))) B(randV)

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接