0

Let's say we have the following C# code:

public bool F(int? a, int? b) {
    return a == b;
}

then the compiler converts it to

public bool F(Nullable<int> a, Nullable<int> b) {
   Nullable<int> num = a;   
   Nullable<int> num2 = b;
   return (num.GetValueOrDefault() == num2.GetValueOrDefault()) & (num.HasValue == num2.HasValue);
}

Notice that & is used instead of $$. But isn't $$ more appropriate and efficient to use because it evaluates the right-hand operand only if it's necessary. If num.GetValueOrDefault() == num2.GetValueOrDefault() is false then there is no need to check num.HasValue == num2.HasValue, but & has to check both. So why the compiler choose to use & instead of &&?

  • 3
    Don't know about this case specifically, but often times it is more efficient to do a redundant compare and bitwise operation than a conditional branch (which shortcircuiting requires). – dxiv Mar 20 '21 at 00:38
  • 3
    What is the `$$` operator? – JoelFan Mar 20 '21 at 00:58
  • Is this about [my answer](https://stackoverflow.com/questions/66701056/why-nullablet-doesnt-overload-opertator/66701155#66701155)? If so, it is worth pointing out that the code is generated by sharplab.io. – Sweeper Mar 20 '21 at 01:07
  • @Sweeper yes. so why the compiler choose to use $ not $$? –  Mar 20 '21 at 01:09
  • 1
    @slowjams That's an implementation detail of the compiler, so I doubt you can find the "true" answer for this, unless the person responsible for this behaviour had said anything about why they did it this way. Nevertheless, you can make some guesses as to why. See dxiv's comment for example. – Sweeper Mar 20 '21 at 01:15
  • @Sweeper I just found this https://learn.microsoft.com/en-us/dotnet/csharp/language-reference/operators/boolean-logical-operators#nullable-boolean-logical-operators it says The conditional logical operators && and || don't support bool? operands, but why? –  Mar 20 '21 at 01:40
  • 1
    That's another question. Note that there is nothing of type `bool?` in the generated code, so the fact hat `&&` and `||` doesn't support `bool?` is irrelevant. – Sweeper Mar 20 '21 at 01:48
  • 2
    looks like you're mistaking `&&` and `$$`. For very short if blocks it's almost always beneficial to have branchless code because [branching is very expensive when you can't predict it](https://stackoverflow.com/q/11227809/995714). That's why compilers will emit `&`/`|` instead of `&&`/`||` in many such situations. Another example: [`(a*b != 0)` is faster than `(a != 0 && b != 0)`](https://stackoverflow.com/q/35531369/995714) because it avoids a branch – phuclv Mar 20 '21 at 05:54
  • 1
    another example: [An expensive jump with GCC 5.4.0](https://stackoverflow.com/q/40991778/995714). Duplicate: [Why short circuit logical operator is supposed to be faster](https://stackoverflow.com/q/47983234/995714), [Short circuit vs non short circuit operators](https://stackoverflow.com/q/18349330/995714) – phuclv Mar 20 '21 at 06:03

0 Answers0