Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/csharp/311.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#_Reference - Fatal编程技术网

C#比较参考值和值

C#比较参考值和值,c#,reference,C#,Reference,我在向它传递值时遇到了这个方法的问题 注意:在我看来,使用此功能的系统是一个黑匣子,因此无法更改 问题是,将相同的值(如字符串、布尔值、对象等)传递给该方法将表示它们不相等,即使这些值相同。我假设这是因为一个是引用,而另一个是值,因此它们“不同” 结果是单元测试全部通过。。。正如“预期的” 因此,当我进行测试时,它会按预期工作,但当我连接到系统的其余部分并进行调试以便可以看到“field”和“value”的值时,它不会工作 以前有人尝试过类似的方法吗?您缺少了相等比较器 正如您在本例中看到的,即

我在向它传递值时遇到了这个方法的问题

注意:在我看来,使用此功能的系统是一个黑匣子,因此无法更改

问题是,将相同的值(如字符串、布尔值、对象等)传递给该方法将表示它们不相等,即使这些值相同。我假设这是因为一个是引用,而另一个是值,因此它们“不同”

结果是单元测试全部通过。。。正如“预期的”

因此,当我进行测试时,它会按预期工作,但当我连接到系统的其余部分并进行调试以便可以看到“field”和“value”的值时,它不会工作


以前有人尝试过类似的方法吗?

您缺少了相等比较器

正如您在本例中看到的,即使等于,输出也将为false:

class Program
{
    static void Main(string[] args)
    {
        Pizza pizza1 = new Pizza(1);
        Pizza pizza2 = new Pizza(1);
        bool equal = AreEqual(pizza1, pizza2);
        Console.WriteLine(equal);
    }

    public static bool AreEqual<T>(T field, T value)
    {
        return EqualityComparer<T>.Default.Equals(field, value);
    }
}

public class Pizza
{
    public Pizza(int slices)
    {
        Slices = slices;
    }
    public int Slices { get; set; }
}
类程序
{
静态void Main(字符串[]参数)
{
比萨饼1=新比萨饼(1);
比萨饼2=新比萨饼(1);
bool equal=arequal(pizza1,pizza2);
控制台写入线(相等);
}
公共静态布尔值相等(T字段,T值)
{
返回EqualityComparer.Default.Equals(字段,值);
}
}
公共级比萨饼
{
公共披萨(整块)
{
切片=切片;
}
公共整数切片{get;set;}
}
输出:

假的


这样,即使使用自定义对象,它也可以工作:

class Program
{
    static void Main(string[] args)
    {
        Pizza pizza1 = new Pizza(1);
        Pizza pizza2 = new Pizza(1);
        bool equal = AreEqual(pizza1, pizza2, new PizzaComparer());
        Console.WriteLine(equal);
    }

    public static bool AreEqual<T>(T field, T value, IEqualityComparer<T> equalityComparer)
    {
        return equalityComparer.Equals(field, value);
    }
}

public class Pizza
{
    public Pizza(int slices)
    {
        Slices = slices;
    }
    public int Slices { get; set; }
}

public class PizzaComparer : IEqualityComparer<Pizza>
{
    public bool Equals(Pizza pizza1, Pizza pizza2)
    {
        return pizza1.Slices == pizza2.Slices;
    }

    public int GetHashCode(Pizza pizza)
    {
        return pizza.Slices.GetHashCode();
    }
}
类程序
{
静态void Main(字符串[]参数)
{
比萨饼1=新比萨饼(1);
比萨饼2=新比萨饼(1);
bool equal=AreEqual(pizza1、pizza2、新PizzaComparer());
控制台写入线(相等);
}
公共静态布尔值相等(T字段、T值、IEqualityComparer相等Comparer)
{
返回equalityComparer.Equals(字段,值);
}
}
公共级比萨饼
{
公共披萨(整块)
{
切片=切片;
}
公共整数切片{get;set;}
}
公共类比萨饼比较器:IEqualityComparer
{
公共布尔等于(比萨披萨1、比萨披萨2)
{
返回pizza1.Slices==pizza2.Slices;
}
公共整数GetHashCode(比萨饼)
{
返回pizza.Slices.GetHashCode();
}
}
输出:

真的


为什么
字段
是通过引用传递的?您不会更改代码中的引用。调试时看到的值是什么?您正在比较浮点数,而使用普通的equals无法真正进行比较。相反,你应该在这里使用一些宽容。通过这种方式,您可以在单元测试中将
12.3
12.3
进行比较,但是当您的值之间存在细微差异时,例如
12.300000001
(可能来自db表)和
12.2999999993
(来自不同的表)。自定义类型可能无法实现相等比较。然后它将退回到默认行为,这可能是引用相等。然后,具有相同内容的对象可能会被视为“不相等”,因为它们不是相同的对象。类似的字符串:他们可能被拘留或没有。因此,可以有相同的字符串(值),但有两个不同的引用。如果您随后检查引用相等性,它将失败。请发布一个显示问题的说明,而不是显示它按您希望的方式工作的代码。我看不出你的代码有什么问题,所以我假设问题在其他地方,在你没有发布的代码中,所以发布一个完整(但简短)的例子,说明这个问题,这样我们就可以自己测试它了。你说这个问题存在于字符串、布尔和对象。对于您自己的类型,您需要为
EqualityComparer.Default
实现一个接口,以便能够对它们进行比较,但对于字符串和bool,这应该可以正常工作。他在问题中说,对于字符串、bool等类型,也存在此问题,这些类型都实现了此接口。
    [TestMethod]
    public void IsDirtyString()
    {
        var tc = new Program();
        var field = "Germany";
        var value = "United States";
        var result = tc.AreEqual(ref field, value);
        Assert.IsFalse(result);
    }
    [TestMethod]
    public void IsNotDirtyString()
    {
        var tc = new Program();
        var field = "Nepal";
        var value = "Nepal";
        var result = tc.AreEqual(ref field, value);
        Assert.IsTrue(result);
    }
    [TestMethod]
    public void IsDirtyDouble()
    {
        var tc = new Program();
        var field = 11.2;
        var value = 12.3;
        var result = tc.AreEqual(ref field, value);
        Assert.IsFalse(result);
    }
    [TestMethod]
    public void IsNotDirtyDouble()
    {
        var tc = new Program();
        var field = 12.3;
        var value = 12.3;
        var result = tc.AreEqual(ref field, value);
        Assert.IsTrue(result);
    }
    [TestMethod]
    public void IsDirtyInt()
    {
        var tc = new Program();
        var field = 12;
        var value = 15;
        var result = tc.AreEqual(ref field, value);
        Assert.IsFalse(result);
    }
    [TestMethod]
    public void IsNotDirtyInt()
    {
        var tc = new Program();
        var field = 12;
        var value = 12;
        var result = tc.AreEqual(ref field, value);
        Assert.IsTrue(result);
    }
    [TestMethod]
    public void IsDirtyBool()
    {
        var tc = new Program();
        var field = true;
        var value = false;
        var result = tc.AreEqual(ref field, value);
        Assert.IsFalse(result);
    }
    [TestMethod]
    public void IsNotDirtyBool()
    {
        var tc = new Program();
        var field = true;
        var value = true;
        var result = tc.AreEqual(ref field, value);
        Assert.IsTrue(result);
    }
class Program
{
    static void Main(string[] args)
    {
        Pizza pizza1 = new Pizza(1);
        Pizza pizza2 = new Pizza(1);
        bool equal = AreEqual(pizza1, pizza2);
        Console.WriteLine(equal);
    }

    public static bool AreEqual<T>(T field, T value)
    {
        return EqualityComparer<T>.Default.Equals(field, value);
    }
}

public class Pizza
{
    public Pizza(int slices)
    {
        Slices = slices;
    }
    public int Slices { get; set; }
}
class Program
{
    static void Main(string[] args)
    {
        Pizza pizza1 = new Pizza(1);
        Pizza pizza2 = new Pizza(1);
        bool equal = AreEqual(pizza1, pizza2, new PizzaComparer());
        Console.WriteLine(equal);
    }

    public static bool AreEqual<T>(T field, T value, IEqualityComparer<T> equalityComparer)
    {
        return equalityComparer.Equals(field, value);
    }
}

public class Pizza
{
    public Pizza(int slices)
    {
        Slices = slices;
    }
    public int Slices { get; set; }
}

public class PizzaComparer : IEqualityComparer<Pizza>
{
    public bool Equals(Pizza pizza1, Pizza pizza2)
    {
        return pizza1.Slices == pizza2.Slices;
    }

    public int GetHashCode(Pizza pizza)
    {
        return pizza.Slices.GetHashCode();
    }
}