IIf()和If之间的性能差异
在Visual Basic中,使用IIf函数代替If语句时,性能会有差异吗?
解决方案
回答
根据这个家伙的说法,IIf最多可以使用If / Then的6倍。 YMMV。
回答
...关于为什么可能需要长达6倍的时间,请引用Wiki:
Because IIf is a library function, it will always require the overhead of a function call, whereas a conditional operator will more likely produce inline code.
IIf本质上等效于C ++ / C#中的三元运算符,因此如果我们愿意,它可以为我们提供一些不错的1行if / else类型语句。我们还可以给它一个评估我们是否需要的功能。
回答
最重要的是,在这种情况下,可读性可能比性能更受青睐。即使IIF效率更高,目标读者也很难理解(我假设如果我们使用的是Visual Basic,我们希望其他程序员能够轻松地阅读代码,这是VB的最大福音。在我看来,这些东西已被诸如IIF之类的概念所迷失了)。
另外," IIF是一个函数,而IF是语言语法的一部分"……对我而言,这确实意味着,If会更快……If除此之外,If语句可以直接分解到一小部分操作码,而不必去存储器中的另一个空间来执行所述功能中发现的逻辑。也许这是个古朴的区别,但值得注意。
回答
IIf()同时运行正确和错误代码。对于简单的事情,例如数字赋值,这没什么大不了的。但是对于需要任何类型处理的代码,我们浪费的是运行不匹配条件的周期,并可能导致副作用。
代码说明:
Module Module1 Sub Main() Dim test As Boolean = False Dim result As String = IIf(test, Foo(), Bar()) End Sub Public Function Foo() As String Console.WriteLine("Foo!") Return "Foo" End Function Public Function Bar() As String Console.WriteLine("Bar!") Return "Bar" End Function End Module
输出:
Foo! Bar!
回答
另外,IIf的另一个大问题是它实际上会调用参数[1]中的任何函数,因此,如果我们遇到以下情况:
string results = IIf(Not oraData.IsDBNull(ndx), oraData.GetString(ndx), string.Empty)
实际上,它将引发异常,这不是大多数人在第一次看到该功能时就认为该功能起作用的方式。这也可能导致一些很难修复的应用程序中的错误。
[1] IIf函数http://msdn.microsoft.com/zh-cn/library/27ydhh0d(VS.71).aspx
回答
我认为该问题涉及的是VB的以下"如果"语句:
' Usage 1 Dim result = If(a > 5, "World", "Hello") ' Usage 2 Dim foo = If(result, "Alternative")
第一个基本上是C#的三元条件运算符,第二个是它的合并运算符(返回"结果",除非其为"无",在这种情况下,返回""替代"")。因此," if"已取代了" IIf",后者已过时。
像在C#中一样,VB的条件if运算符发生短路,因此我们现在可以安全地编写以下内容,而使用IIf函数则无法实现:
Dim len = If(text Is Nothing, 0, text.Length)
回答
更好地使用If而不是IIf来正确使用类型推断机制(Option Infer On)
在此示例中,当我使用If时,关键字被识别为字符串:
Dim Keywords = If(String.IsNullOrEmpty(SelectedKeywords), "N/A", SelectedKeywords)
否则,将其识别为Object:
Dim Keywords = IIf(String.IsNullOrEmpty(SelectedKeywords), "N/A", SelectedKeywords)
回答
我认为If和IIf之间的主要区别是:
- if(test [boolean],statement1,statement2)表示根据测试值,将执行satement1或者statement2(仅执行一条语句)
- Dim obj = IIF(test [boolean],statement1,statement2)意味着这两个语句都将执行,但是根据测试值,其中一个将返回一个值给(obj)。
因此,如果其中一条语句将引发异常,则无论如何它都会将其引发到(IIf)中,但在(If)中它将引发该异常,以防万一条件将返回其值。