Why is the result of adding two null strings not n

2019-02-07 16:33发布

This question already has an answer here:

I was fiddling around in C# when I came across this weird behavior in .Net programming.

I have written this code:

  static void Main(string[] args)
    {
        string xyz = null;
        xyz += xyz;
        TestNullFunc(xyz);
        Console.WriteLine(xyz);

        Console.Read();

    }

    static void TestNullFunc(string abc)
    {
        if (abc == null)
        {
            Console.WriteLine("meow THERE ! ");
        }
        else
        {
            Console.WriteLine("No Meow ");
        }
    }

I got the output as No meow, which means the string is not null. How is this possible? Why does adding two null strings, result in a non-null string?

On debugging when I check the value of xyz after adding it to itself, its value is "" (no characters).

标签: c# string null
6条回答
ゆ 、 Hurt°
2楼-- · 2019-02-07 16:35

From MSDN:

In string concatenation operations, the C# compiler treats a null string the same as an empty string,

Even though xyz is null, calling the += operator (which is converted to a call to the + operator (*)) on it does not throw a NullReferenceException because it's a static method. In pseudo code:

xyz = String.+(null, null);

The implementation will then interpret this as if it was

xyz = String.+("", "");

(*) Section §7.17.2 of the C# specification:

An operation of the form x op= y is processed by applying binary operator overload resolution (§7.3.4) as if the operation was written x op y.

查看更多
我只想做你的唯一
3楼-- · 2019-02-07 16:35

Thats because the Operator += adds the Null to Empty string.

so, the Compiler does Adding Empty String to the Existing string Object.

So it is Empty and Not null.

查看更多
欢心
4楼-- · 2019-02-07 16:40

When you use the += operator, you are actually calling the string.Concat method, that, as stated in the documentation:

The method concatenates str0 and str1; it does not add any delimiters. An Empty string is used in place of any null argument.

In fact this code:

string xyz = null;
xyz += xyz;

will be compiled in:

IL_0000:  ldnull      
IL_0001:  stloc.0     // xyz
IL_0002:  ldloc.0     // xyz
IL_0003:  ldloc.0     // xyz
IL_0004:  call        System.String.Concat
IL_0009:  stloc.0     // xyz
查看更多
手持菜刀,她持情操
5楼-- · 2019-02-07 16:53

try this...

static void TestNullFunc(string abc)
{
    if (string.IsNullOrEmpty( abc))
    {
        Console.WriteLine("meow THERE ! ");
    }
    else
    {
        Console.WriteLine("No Meow ");
    }
}
查看更多
Viruses.
6楼-- · 2019-02-07 16:59

C# borrows the behavior of its + operator from Java. If either operand to + is a string, the + operator will call String.Concat, which accepts type Object and concatenates the results of calling ToString on every non-null object that's passed to it. The fact that null references are simply ignored is only a small part of the way in which the operands to String.Concat aren't regarded as "strings" per se; a much more noticeable aspect of this behavior is that types which aren't strings have their ToString method called, whether or not they would otherwise be implicitly convertible to string.

查看更多
倾城 Initia
7楼-- · 2019-02-07 17:00

As stated, the reason why is that concatenating null is taken to be the same as concatenating an empty string.

It's worth considering why this behaviour is useful.

Normally, there are two sensible things we can do with an binary operator when one of the operands is null:

  1. The result is null.
  2. The operation is a no-op, and we're left with the other operand.

It makes sense for instance, that ((int?)null) + 3 results in null, and generally either this will be the most useful result, or one we will consciously guard against (that is, we'll add code to catch the null case explicitly).

But there are two reasons to not do this with string concatenation.

The first is to consider, that since concatenation means not an arithmetic calculation, but sticking two things together, then what is the most reasonable result of sticking null onto the beginning or end of something? It's easy to make the case that this should do nothing, rather than return null.

The second is that in practice, there will be fewer cases where we want a + b + c + d with strings to return null if any of those are null, than cases where we would not.

And from that, it makes sense to treat null as an empty string in concatenations. From that basis, that (string)null + (string)null results in "" is because we don't have a special case for concatenating too nulls.

That special case could be added, but then the property that x + "" == x + null would no longer hold, which could lead to some strange cases.

查看更多
登录 后发表回答