为什么给字符串添加null没有异常?

发布于 2024-09-10 16:24:04 字数 116 浏览 5 评论 0原文

为什么这不抛出异常不明白,obj 为 null

object obj = null;
Console.WriteLine("Hello World " + obj);

Why doesnt this throw an exception dont understand, obj is null

object obj = null;
Console.WriteLine("Hello World " + obj);

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(5

许久 2024-09-17 16:24:04

这将编译为

Console.WriteLine(String.Concat("Hello World ", obj));

String.Concat 方法 忽略 null 参数。

它的定义如下:(来自.Net参考源)

    public static String Concat(Object arg0, Object arg1) {
        if (arg0==null) {
            arg0 = String.Empty; 
        }

        if (arg1==null) { 
            arg1 = String.Empty;
        } 
        return Concat(arg0.ToString(), arg1.ToString());
    }

我不知道为什么它不简单地返回arg1.ToString() if arg0==null

String.Concat(string, string) 方法定义如下:

    public static String Concat(String str0, String str1) { 
        if (IsNullOrEmpty(str0)) { 
            if (IsNullOrEmpty(str1)) {
                return String.Empty; 
            }
            return str1;
        }

        if (IsNullOrEmpty(str1)) {
            return str0; 
        } 

        int str0Length = str0.Length; 

        String result = FastAllocateString(str0Length + str1.Length);

        FillStringChecked(result, 0,        str0); 
        FillStringChecked(result, str0Length, str1);

        return result; 
    }

This compiles to

Console.WriteLine(String.Concat("Hello World ", obj));

The String.Concat method ignores null parameters.

It's defined like this: (From the .Net reference source)

    public static String Concat(Object arg0, Object arg1) {
        if (arg0==null) {
            arg0 = String.Empty; 
        }

        if (arg1==null) { 
            arg1 = String.Empty;
        } 
        return Concat(arg0.ToString(), arg1.ToString());
    }

I don't know why it doesn't simply return arg1.ToString() if arg0==null.

The String.Concat(string, string) method is defined like this:

    public static String Concat(String str0, String str1) { 
        if (IsNullOrEmpty(str0)) { 
            if (IsNullOrEmpty(str1)) {
                return String.Empty; 
            }
            return str1;
        }

        if (IsNullOrEmpty(str1)) {
            return str0; 
        } 

        int str0Length = str0.Length; 

        String result = FastAllocateString(str0Length + str1.Length);

        FillStringChecked(result, 0,        str0); 
        FillStringChecked(result, str0Length, str1);

        return result; 
    }
不喜欢何必死缠烂打 2024-09-17 16:24:04

null 参数传递给方法并不一定会引发异常;这取决于方法的实现(在这种情况下,您可能会看到 ArgumentNullException)。

尝试访问 null 对象**的成员*将会始终抛出NullReferenceException,保证* **。

所以...

可能会或可能不会抛出异常

object obj = null;
SomeMethod(obj); // passing as parameter

肯定会抛出异常

object obj = null;
int hashCode = obj.GetHashCode(); // calling instance method

在有问题的代码的情况下,您传递给Console.WriteLine的参数实际上是对 string.Concat 的编译调用的结果,它允许将 null 值作为参数传递,并本质上忽略它们 - 如 SLAks 已经指出了


*扩展方法是另一回事;可以在“空”参数上调用它们;但由于这些仅呈现出像实例方法一样的幻觉,因此该规则不适用于它们。事实上,扩展方法毕竟只是静态方法。如果您在 null 值上调用一个,则实际上是将 null 作为参数传递。

**这里我不包括 >Nullable 值,HasValue == false;尽管在许多情况下这些可以方便地被视为 null,但这只是为了语法方便:它们不比任何其他值类型都 null 更 null.

***我在这里谈论的是 C#。正如 SLAks 在评论中指出的那样,这不是 CLI 本身的规则。但 C# 中的所有实例方法调用都会编译为 IL 中的 callvirt 指令,如果实例为 null,则该指令抛出异常。

Passing a null parameter to a method is not necessarily going to throw an exception; that's up to the implementation of the method (and in that case you'd probably see an ArgumentNullException).

Attempting to access a member* of a null object** is what will always throw a NullReferenceException, guaranteed***.

So...

May or may not throw an exception

object obj = null;
SomeMethod(obj); // passing as parameter

Will definitely throw an exception

object obj = null;
int hashCode = obj.GetHashCode(); // calling instance method

In the case of the code in question, the parameter you are passing to Console.WriteLine is actually the result of a compiled call to string.Concat, which allows null values to be passed as parameters and essentially ignores them -- as SLaks already pointed out.


*Extension methods are a different matter; they can be called on "null" parameters; but since these only present the illusion of acting like instance methods, this rule does not apply to them. In fact, extension methods are after all just static methods. If you call one "on" a null value, you are effectively passing null as a parameter.

**Here I am not including Nullable<T> values with HasValue == false; though these might conveniently be treated as null in many cases, this is just for syntactical convenience: they are no more null than any other value type can ever be null.

***I'm talking about C# here. As SLaks points out in a comment, this is not a rule of the CLI itself. But all instance method calls in C# are compiled to callvirt instructions in IL, which will throw an exception if the instance is null.

二货你真萌 2024-09-17 16:24:04

因为那会很烦人。对于大多数目的来说,空字符串和空字符串之间没有语义差异。

Because that would be annoying. For most pruposes there is no semantic difference between an empty and a null string.

掌心的温暖 2024-09-17 16:24:04

如果您遇到在实际应用程序中可能发生这种情况的问题,您可以随时在显示文本之前检查是否为空。然后,您可以显示替代文本,或者不显示任何内容。

If you have an issue where this might occur in a real application, you could always check for null before displaying the text. Then, you could display an alternate text, or nothing.

瑕疵 2024-09-17 16:24:04

因为他们实现了 String.IsNullOrEmpty 并将其留给我们来弄清楚如何使用它。

Because they implemented String.IsNullOrEmpty and left it to us to figure out how to use it.

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文