Warning: file_get_contents(/data/phpspider/zhask/data//catemap/0/performance/5.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C# 否则哪个更快?:_C#_Performance_If Statement - Fatal编程技术网

C# 否则哪个更快?:

C# 否则哪个更快?:,c#,performance,if-statement,C#,Performance,If Statement,c语言中哪个更快 int a = 10; bool _IsEven; if(a%2 == 0) { _IsEven = true; } else { _IsEven = false; } 或 更新 我知道在这里我可以优化我的代码,只需编写 bool _IsEven = a%2 == 0; 但我的问题不是关于代码优化,而是关于这两条语句的性能 你能帮我提高我的编码知识吗?你的第二个代码甚至无法编译。但你可以写: bool isEven = a % 2 == 0; x = cond

c语言中哪个更快

int a = 10;
bool _IsEven;
if(a%2 == 0)
{
   _IsEven = true;
}
else
{
   _IsEven = false;
}

更新

我知道在这里我可以优化我的代码,只需编写

bool _IsEven = a%2 == 0;
但我的问题不是关于代码优化,而是关于这两条语句的性能


你能帮我提高我的编码知识吗?

你的第二个代码甚至无法编译。但你可以写:

bool isEven = a % 2 == 0;
x = condition;

为什么要使用条件运算符或if语句

通常,当您有以下情况时:

if (condition)
{
    x = true;
}
else
{
    x = false;
}

你可以写:

bool isEven = a % 2 == 0;
x = condition;
无论如何,看到C编译器优化这一点我都不会感到惊讶,但我不会像关注可读性那样关注性能。

根据这一点,if..else块的运行速度与?:三元运算的运行速度一样快,与单级switch/case语句的运行速度一样快

因此,在我看来,与其担心性能,不如追求更好的可读性和更清晰的陈述,因为它对您的情况影响最小。

编辑:如果没有其他内容,请阅读底部的结论。Rest试图向普通读者解释为什么结论是有意义的

请注意,我对这个问题的直接反应是,这不重要。从最实际的角度来看,你不应该发现任何不同。。。任何人都可能会说,它们只是实现同一目标的两种不同方式。。。尽管可读性当然可能有所不同,但这取决于编写这些语句所涉及的实际三种表达方式。i、 e

条件表达式 表达式,如果条件为true 表达式,如果条件为false 最重要的是,正如其他人所建议的,您应该能够通过我假设的发布版本来理解这一点

查看生成的IL。 使用大量迭代对代码进行计时。 但是,假设你对微优化感兴趣,不管原因是好是坏,我也很好奇,自己也看了看。。纯粹是为了消遣,这就是我发现的-

注:以下调查结果不得视为绝对结果,因为

它们可能取决于几个我不知道的因素,包括我在测试中选择的上面提到的3个表达式。 任何人都会争辩说,即使所有因素都已知,其中许多都是C编译器或JIT编译器的内部细节,因此可以随任一编译器的任何版本而改变。我在我的机器上做了一个奇怪的小实验。NET4.5,发布版本。 实验1 代码

h=a=b的IL?10 : -10;

h=a=b的装配?10 : -10;

如果a==bh=10,则为IL;否则h=-10

分析 我重复一遍,不是来自C或JIT编译器团队,这一分析只是我的猜测,我可能已经犯了错误,错误的假设,并且很可能,作为实现细节,在未来的版本中可能会发生更改。最后,但并非最不重要的一点是,优化很可能是由这里根本没有考虑的几个其他因素/变化驱动的

基于IL:

为实验1生成的IL看起来更好,因为虽然最终结果明显相同,但编译器似乎确实为实验2生成了1条额外的IL指令。i、 e.if块和else块的每个表达式似乎都被视为独立的,因此,虽然您和我都知道代码涉及到对变量h的赋值,但编译器将这两个代码块视为单独的,并生成独立代码以赋值给h if..else。。使用

dword ptr[ebp-14h]显然是一个临时变量,它存储上述表达式2条件为真或表达式3条件为假的结果。。行为可能完全因表达式本身而异。。我不知道。。然后必须将值从临时变量移到CPU寄存器,然后从CPU寄存器移到堆栈上为局部变量h分配的位置

IL_0008:  bne.un.s   IL_000f
IL_000a:  ldc.i4.s   10
IL_000c:  stloc.2
IL_000d:  br.s       IL_0012
IL_000f:  ldc.i4.s   -10
IL_0011:  stloc.2

00862896  mov         dword ptr [ebp-10h],0Ah          <-- IL_000a:  ldc.i4.s   10
                                                       <-- IL_000c:  stloc.2

008628A0  mov         dword ptr [ebp-10h],0FFFFFFF6h   <-- IL_000f:  ldc.i4.s   -10
                                                       <-- IL_0011:  stloc.2
在这里,很明显,值10需要加载到堆栈上的一个潜在临时变量,然后立即从该位置移动到堆栈上变量h的位置。我想,通过让两个加载和存储指令紧挨着彼此,JITter应该很容易就能看出它可以直接将值存储到局部变量中,而不需要临时变量。因此,似乎未优化的IL代码在生成汇编代码抖动时应该表现得更好

结论 虽然这是我个人的选择,花我的时间在晚上写这一长的答案,任何人谁读了通过这一点,以达到我的最终结论,我的荣誉

微观优化不仅会因更高的语言级别结构而有所不同,还会因各种其他因素而有所不同,这些因素可能不在您的控制范围之内。。我猜,3个表达式中的代码与您选择的if..else..一样重要。。vs?:,以及com的版本 使用了piler和runtime,以及操作系统上的其他条件

因此,假设微优化对您来说非常重要,除非您已经准备好运行性能测试,因为您的特定代码忽略了另一个答案中提供的基准测试。。在许多情况下,为这些微优化运行您自己的测试本身可能非常困难,因为它们很容易受到外部的、系统范围的因素的影响,如OS Scheduler等。随着您在该代码中所做的每一次更改/每次运行时版本更改以检查性能退化,您遇到的问题毫无意义,你的问题没有绝对的答案


PS-我希望,这个答案能成为关于堆栈溢出的此类通用微优化/性能问题的一个很好的例子,几乎每天都会遇到:。

将每个问题放入一个循环中,并测量运行它们100万次所需的时间。看看生成的IL,看看它们之间的区别。嘿,Nadeem_MK,这只是我解释问题的一个例子。如果他们有很多条件需要检查呢???那么一切都取决于条件。要进行验证,可以做的一件事是将条件放入循环中,并记录执行时间。
int a = 1;
int b = 2;
int h = 0;

h = a == b ? 10 : -10;
GC.KeepAlive(h);
IL_0006:  ldloc.0
IL_0007:  ldloc.1
IL_0008:  beq.s      IL_000e
IL_000a:  ldc.i4.s   -10
IL_000c:  br.s       IL_0010
IL_000e:  ldc.i4.s   10
IL_0010:  stloc.2
00482B61  mov         eax,dword ptr [ebp-8]  
00482B64  cmp         eax,dword ptr [ebp-0Ch]  
00482B67  je          00482B73  
00482B69  nop  
00482B6A  mov         dword ptr [ebp-14h],0FFFFFFF6h  
00482B71  jmp         00482B7A  
00482B73  mov         dword ptr [ebp-14h],0Ah  
00482B7A  mov         eax,dword ptr [ebp-14h]  <-- Extra compared to 2nd experiment
00482B7D  mov         dword ptr [ebp-10h],eax  <-- Extra compared to 2nd experiment
int a = 1;
int b = 2;
int h = 0;

if (a == b) h = 10; else h = -10;
GC.KeepAlive(h);
IL_0006:  ldloc.0
IL_0007:  ldloc.1
IL_0008:  bne.un.s   IL_000f
IL_000a:  ldc.i4.s   10
IL_000c:  stloc.2                              <-- Extra compared to 1st experiment
IL_000d:  br.s       IL_0012
IL_000f:  ldc.i4.s   -10
IL_0011:  stloc.2
0086288E  mov         eax,dword ptr [ebp-8]  
00862891  cmp         eax,dword ptr [ebp-0Ch]  
00862894  jne         008628A0  
00862896  mov         dword ptr [ebp-10h],0Ah  
0086289D  nop  
0086289E  jmp         008628A7  
008628A0  mov         dword ptr [ebp-10h],0FFFFFFF6h  
IL_000c:  stloc.2                              <-- Extra compared to 1st experiment
....
IL_0011:  stloc.2
IL_0008:  beq.s      IL_000e
IL_000a:  ldc.i4.s   -10
IL_000c:  br.s       IL_0010
IL_000e:  ldc.i4.s   10
IL_0010:  stloc.2


00482B6A  mov         dword ptr [ebp-14h],0FFFFFFF6h   <-- IL_000a:  ldc.i4.s   -10

00482B73  mov         dword ptr [ebp-14h],0Ah          <-- IL_000e:  ldc.i4.s   10
00482B7A  mov         eax,dword ptr [ebp-14h]          <-- IL_0010:  stloc.2
00482B7D  mov         dword ptr [ebp-10h],eax          <-- IL_0010:  stloc.2
IL_0008:  bne.un.s   IL_000f
IL_000a:  ldc.i4.s   10
IL_000c:  stloc.2
IL_000d:  br.s       IL_0012
IL_000f:  ldc.i4.s   -10
IL_0011:  stloc.2

00862896  mov         dword ptr [ebp-10h],0Ah          <-- IL_000a:  ldc.i4.s   10
                                                       <-- IL_000c:  stloc.2

008628A0  mov         dword ptr [ebp-10h],0FFFFFFF6h   <-- IL_000f:  ldc.i4.s   -10
                                                       <-- IL_0011:  stloc.2