带有 case OR-ing 的 VB.NET 选择 case 语句逻辑是啥?

Posted

技术标签:

【中文标题】带有 case OR-ing 的 VB.NET 选择 case 语句逻辑是啥?【英文标题】:What is the VB.NET select case statement logic with case OR-ing?带有 case OR-ing 的 VB.NET 选择 case 语句逻辑是什么? 【发布时间】:2009-02-17 00:57:12 【问题描述】:

我在 case 表达式中使用了 Or 语句。

即使我有这个范围内的值,它也没有找到匹配项。为什么不呢?

示例代码

Select Case 2
    Case 0
        ' Some logic

    Case 1
        ' Some other logic

    Case 2 Or 3
        Console.WriteLine("hit")

 End Select

根据上述情况,我假设hit 会被打印出来,但事实并非如此。

【问题讨论】:

【参考方案1】:

使用逗号分隔 case 语句

Select Case 2
    Case 0,1,2,3
        Console.WriteLine("hit")
 End Select

【讨论】:

我的意图不是让案例 0 和案例 1 失败。但逗号是我所追求的。 -1,因为它没有回答所述问题。相反,它为提问者尝试的解决方案提供了另一种解决方案。问题是:VB 如何解释 Select 语句中的 OR 运算符?否则,必须编辑问题以匹配答案。但我不建议这样做,因为@JohnT 给出了正确的答案。 @Geoffrey,嗯,OP 都接受了我的回答并承认这是他们所追求的。 我知道。 @vanslly 必须重述问题,但随后回答正确的 @JohnT 将失分。 @Geoffrey,IMO 了解 OP 的意图比准确回答他的要求更重要。法律条文与法律精神之间是同一个概念。两者都是正确的,但我认为法律的精神(即他的意图)更正确。【参考方案2】:

正如Jared所说,你需要使用逗号来分隔case语句。

您正在执行的Or 是按位或,导致它为“3”。有趣的是,“2 AND 3”可能适用于您的具体情况。

【讨论】:

【参考方案3】:

JaredPar 是对的,但您也可以使用 To 构造

Select Case 2
    Case 0,1
    Case 2 To 3
        Console.WriteLine("Hit")
End Select

这将是 0 或 1 什么都不做,2 或 3 打印 Hit...To 构造是一个范围...

Here's the MSDN

【讨论】:

是的,我使用的是 To 关键字,但它有点 hacky 因为如果说 2 和 3 是 Enum vals 并且枚举在不考虑这种用途的情况下被重构 - 如果它在某个类中很深在一个大系统的内部——然后你会有一些意想不到的中断;)【参考方案4】:

编辑: 看来我假设 VB.NET 不允许大小写 ORing 是错误的。我在用 C# 和 IL 思考,看来我错了。

但是,正如有人指出的那样,您的代码不起作用的原因是因为案例 2 或 3 将 2 或 3 评估为按位或,因此评估为案例 3。

澄清:


       2 binary = 0000 0010
       3 binary = 0000 0011
  2 Or 3 binary = 0000 0011 (= 3)

  Select Case 2
     Case 0            '--> no match

     Case 1            '--> no match

     Case 2 Or 3       '(equivalent to Case 3  --> no match)
   End Select

但是,我觉得我应该指出,为了性能,不应该使用这样的构造。当编译器遇到 Select 语句(C# 中的 switch)时,它会尝试使用查找表和 switch MSIL 指令来编译它们,但如果你有类似 案例 1,2,11,55 编译器将无法将其转换为查找表,它必须使用一系列比较(就像使用 If.. Else)。

关键是,为了真正利用 Select 语句,在设计案例时应考虑到这一点。否则,唯一的好处就是代码可读性。

设计良好的开关是 O(1) 操作,而设计不佳的开关(相当于一系列 If..Then..Else 语句)是 O(n) 操作。

【讨论】:

谢谢,这让我现在可以休息了。从逻辑上阅读代码并没有给我任何暗示我做错了什么。 我很高兴您能够找到您想要解决的问题的答案,我希望我在答案中添加的说明将帮助您制作更好的 Select 语句 :)【参考方案5】:

这将允许您在 0 的情况下执行“something”,在 1 的情况下执行“something else”,在 2 或 3 的情况下执行“hit”或“hit else”。

Select Case 2
    Case 0
        Console.WriteLine("something")
    Case 1
        Console.WriteLine("something else")
    Case Is 2 To 3
        Console.WriteLine("hit")
    Else
        Console.WriteLine("hit else")
 End Select

【讨论】:

【参考方案6】:

大部分或所有这些答案都忽略了目的失败(或转到案例):

不必重用代码或只为同一Select Case/If Tree 中的几个区域创建特殊功能,这样您就可以避免重用代码,例如这个 javascript

这些示例非常做作。肯定有方法可以简化这种情况,但很多时候没有。

let pay = 100, perks = '';
Switch (EmpObj.type) 
  Case 'Boss':
    pay = pay * 10;
    perks = '11 month vacation per year';
  Case 'Manager':
    pay = pay * 3; // This will make Boss pay * 30
  Case 'Employee':
    EmpObj.pay = pay;
    EmpObj.perks = perks;
    break;
  Case 'Intern':
    EmpObj.sendMessage("Go get some coffee.")
 

在 VB.net 中,相同的代码将是

dim pay = 100, perks = "";
Switch (EmpObj.type) 
  Case "Boss":
    pay = pay * 30
    perks = "11 month vacation per year"
  Case "Manager":
    pay = pay * 3
  Case "Employee":
  Case 'Intern':
    pay = 0
    EmpObj.sendMessage("Go get some coffee.")
End Select

EmpObj.pay = pay;
EmpObj.perks = perks;

在简单的情况下,case 比比较 if-branch 更容易读写,但 fall-through 是最好的部分。

有一种方法至少现在可以使用在 Visual Basic 2017 中。虽然它不是最漂亮的。

GoTo Case "[label]"Goto [Case-label] 仍然不起作用。

标签(此处为Number2)必须在Case 之后。那是最令人失望的部分。

dim Value = "1"
Select Case Value
    Case "0"
       ' do nothing, example
    Case "1"
        MsgBox("one")
        GoTo Number2
    Case "2"
Number2:
        MsgBox("two")
    Case "boolean"
        MsgBox("three")
        ' just to show it won't fall through
End Select

【讨论】:

以上是关于带有 case OR-ing 的 VB.NET 选择 case 语句逻辑是啥?的主要内容,如果未能解决你的问题,请参考以下文章

[VB.NET]Select Case语句拾遗

VB.NET 将 Select Case 语句堆叠在一起,就像在 Switch C#/Java 中一样

vb.net 点击按钮选中listview最后一行

将可选枚举传递给 VB.NET 中的函数

制作一组单选按钮 [VB.NET]

VB.NET 根据所选文化格式化数字