简体   繁体   English

对象数组中相等性的字符串比较:意外的false

[英]String comparison for equality in an object array: unexpected false

Consider the following: 考虑以下:

using System;

namespace ObjectArrayWeirdness
{
    public class Program
    {
        public static object[] Change(object[] set)
        {
            object[] result = new object[set.Length];

            // If the following two lines are replaced with:
            // result[0] = "ab";
            // then ArrayEquals will evaluate true.
            result[0] = "a";
            result[0] += "b";
            return result;
        }

        public static bool ArrayEquals(object[] a, object[] b)
        {
            if (a.Length != b.Length) return false;
            for (int i = 0; i < a.Length; i++)
            {
                if (a[i] != b[i])
                {
                    return false;
                }
            }
            return true;
        }


        static void Main(string[] args)
        {
            object[] expected = { "ab" };
            object[] actual = Change(new object[] { 1 });
            Console.WriteLine(ArrayEquals(expected, actual));
        }
    }
}

Dotnetfiddle for convenience Dotnetfiddle为方便

Output: 输出:

false

Output of result[0].GetType() : 输出result[0].GetType()

System.String

My questions: 我的问题:

  1. Does the comparison in ArrayEquals fail because it's comparing object reference and not value? ArrayEquals的比较是否因为比较对象引用而不是值而失败?

  2. If that's the case, why does it succeed when the correct string is assigned in one step (without using += ) into result[0] ? 如果是这样,为什么在一步中(不使用+= )将正确的字符串分配给result[0]时,为什么成功?

I must admit I expected normal string comparison given that GetType() identifies both a[0] and b[0] as strings. 我必须承认我期望正常的字符串比较,因为GetType()a[0]b[0]都识别为字符串。

Does the comparison in ArrayEquals fail because it's comparing object reference and not value? ArrayEquals中的比较是否因为比较对象引用而不是值而失败?

Yes

If that's the case, why does it succeed when the correct string is assigned in one step (without using +=) into result[0]? 如果是这种情况,为什么一步一步将正确的字符串分配给result [0]时,为什么成功?

This is a compiler optimization. 这是编译器优化。 When you declare two literal strings that are the same at compile time, the compiler collapses them into a single object instance to save space. 当您在编译时声明两个相同的文字字符串时,编译器会将它们折叠到单个对象实例中以节省空间。 But if the string is constructed at run time, you'll end up with two separate string objects. 但是,如果字符串是在运行时构造的,则最终会有两个单独的字符串对象。

That exactly what happens. 那正是发生了什么。 You are comparing object reference. 您正在比较对象引用。 Note however that string overrides the == and != operators to compare literals. 但是请注意,字符串会覆盖==!=运算符以比较文字。 So your comparison will work as you expect it if you cast the array items to string: 因此,如果将数组项转换为字符串,则比较将按预期工作:

if ((string)a[i] != (string)b[i])
{
    return false;
}

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM