简体   繁体   English

对诸如温度之类的 UOM 使用结构体有什么好处?

[英]What is the advantage of using structs for UOMs like Temperature?

I ran the code below to test speed of some common uses in my program for UOM's and was quite surprised.我运行下面的代码来测试我的程序中一些常见用途的 UOM 速度,并感到非常惊讶。 With the results: All tests were run 1 million times in debug mode (run mode gave similar differences).结果:所有测试都在调试模式下运行了 100 万次(运行模式给出了类似的差异)。 It seems there is no real advantage in using structs for UOMs from a speed point of view so can anyone tell what any advantages would be?从速度的角度来看,为 UOM 使用结构似乎没有真正的优势,所以有人能说出有什么优势吗? (I have a big number crunching program and this is of huge interest to me). (我有一个很大的数字运算程序,这对我很感兴趣)。 If the example code is wrong in any way below, please let me know also.如果下面的示例代码有任何错误,也请告诉我。 What I really want is the most convenient way to handle UOMs without making the code verbose (UOM * UOM rather than UOM.Value * UOM.Value would be best but its apparently not the most speed efficient).我真正想要的是在不使代码冗长的情况下处理 UOM 的最方便的方法(UOM * UOM 而不是 UOM.Value * UOM.Value 是最好的,但它显然不是最有效的速度)。 All times in ms.所有时间都以毫秒为单位。

Multply doubles 7乘以双 7

Multply struct fields 8将结构字段相乘 8

Multply struct property 232乘法结构属性 232

Multply temperature struct using overloaded * operator 141使用重载 * 运算符 141 的乘法温度结构

Multply class fields 7乘以类字段 7

Multiply & Load doubles into object array 692乘以和加载双倍到对象数组 692

Multiply struct fields & Load into object array 719将结构字段相乘并加载到对象数组中 719

Multiply struct fields & Load new struct into object array 926将结构字段相乘并将新结构加载到对象数组中 926

Multiply structs with overloaded operator a load struct into object array 906将具有重载运算符的结构与加载结构相乘到对象数组 906

Multiply class fields & load into object array 697乘以类字段并加载到对象数组 697

Multiply class fields & load new class into object array 964将类字段相乘并将新类加载到对象数组中 964

Multiply class using overloaded * operator & load class into object array 948使用重载的 * 运算符将类相乘并将类加载到对象数组中 948

public class TestSpeed
{
    public class TempClass
    {
        public double value=100;
        private double v;

        public TempClass(double v)
        {
            this.v = v;
        }

        public static TempClass operator *(TempClass t1, TempClass t2)
        {
            return new TempClass(t1.value * t2.value);
        }
    }

    public struct TempStruct
    {
        public double value;

        public TempStruct(double v)
        {
            value = v;
        }

        public double GetTemp
        {
            get { return value; }
            set { this.value = value; }
        }

        public static TempStruct operator *(TempStruct t1, TempStruct t2)
        {
            return new TempStruct(t1.value * t2.value);
        }
    }


    [TestMethod]
    public void TestDouble()
    {
        double doubleValue = 100;
        TempStruct t = new TempStruct();
        TempStruct Tres= new TempStruct(100);
        TempClass tclass = new TempClass(100);
        double res;

        var watch = Stopwatch.StartNew();

        for (int i = 0; i < 10000000; i++)
        {
            res = doubleValue*doubleValue;
        }

        watch.Stop();

        var elapsedMs = watch.ElapsedMilliseconds;
        Debug.WriteLine("Multply doubles "+ elapsedMs.ToString());

        watch = Stopwatch.StartNew();

        for (int i = 0; i < 10000000; i++)
        {
            Tres.value = t.value * t.value;
        }

        watch.Stop();


        elapsedMs = watch.ElapsedMilliseconds;
        Debug.WriteLine("Multply struct fields " + elapsedMs.ToString());

        watch = Stopwatch.StartNew();

        for (int i = 0; i < 10000000; i++)
        {
            Tres.GetTemp = t.GetTemp * t.GetTemp;
        }

        watch.Stop();


        elapsedMs = watch.ElapsedMilliseconds;
        Debug.WriteLine("Multply struct property " + elapsedMs.ToString());


        watch = Stopwatch.StartNew();

        for (int i = 0; i < 10000000; i++)
        {
            Tres = t * t;
        }

        watch.Stop();

        elapsedMs = watch.ElapsedMilliseconds;
        Debug.WriteLine("Multply temperature struct using overloaded * operator " + elapsedMs.ToString());

        watch = Stopwatch.StartNew();

        for (int i = 0; i < 10000000; i++)
        {
            res = tclass.value * tclass.value;
        }

        watch.Stop();
        elapsedMs = watch.ElapsedMilliseconds;
        Debug.WriteLine("Multply class fields " + elapsedMs.ToString());
    }


    [TestMethod]
    public void TestDoubleArray()
    {
        double doublevalue = 100;
        TempStruct t = new TempStruct();
        TempStruct Tres = new TempStruct(100);
        TempClass tclass = new TempClass(100);
        object[] res = new object[10000000];

        var watch = Stopwatch.StartNew();

        for (int i = 0; i < 10000000; i++)
        {
            res[i] = doublevalue * doublevalue;
        }

        watch.Stop();

        var elapsedMs = watch.ElapsedMilliseconds;
        Debug.WriteLine("Multiply & Load doubles into object array " + elapsedMs.ToString());

        watch = Stopwatch.StartNew();

        for (int i = 0; i < 10000000; i++)
        {
            res[i] = t.value * t.value;
        }

        watch.Stop();


        elapsedMs = watch.ElapsedMilliseconds;
        Debug.WriteLine("Multiply struct fields & Load into object array " + elapsedMs.ToString());


        watch = Stopwatch.StartNew();

        for (int i = 0; i < 10000000; i++)
        {
            res[i] = new TempStruct(t.value * t.value);
        }

        watch.Stop();


        elapsedMs = watch.ElapsedMilliseconds;
        Debug.WriteLine("Multiply struct fields & Load new struct into object array " + elapsedMs.ToString());



        watch = Stopwatch.StartNew();

        for (int i = 0; i < 10000000; i++)
        {
            res[i] = t * t;
        }

        watch.Stop();

        elapsedMs = watch.ElapsedMilliseconds;
        Debug.WriteLine("Multiply structs with overloaded operator a load struct into object array " + elapsedMs.ToString());

        watch = Stopwatch.StartNew();

        for (int i = 0; i < 10000000; i++)
        {
            res[i] = tclass.value * tclass.value;
        }

        watch.Stop();
        elapsedMs = watch.ElapsedMilliseconds;
        Debug.WriteLine("Multiply class fields & load into object array " + elapsedMs.ToString());

        watch = Stopwatch.StartNew();

        for (int i = 0; i < 10000000; i++)
        {
            res[i] = new TempClass(tclass.value * tclass.value);
        }

        watch.Stop();
        elapsedMs = watch.ElapsedMilliseconds;
        Debug.WriteLine("Multiply class fields & load new class into object array " + elapsedMs.ToString());

        watch = Stopwatch.StartNew();

        for (int i = 0; i < 10000000; i++)
        {
            res[i] = tclass * tclass;
        }

        watch.Stop();
        elapsedMs = watch.ElapsedMilliseconds;
        Debug.WriteLine("Multiply class using overloaded * operator & load class into object array " + elapsedMs.ToString());
    }
}    

The difference between struct and class is memory allocation. struct 和 class 之间的区别在于内存分配。 Using class, you have a very small overhead.使用类,您的开销非常小。 So you wont be able to notice the performance overhead.所以你不会注意到性能开销。

Then the point of using struct is not using reference.那么使用 struct 的重点不是使用引用。 Hence you dont need to worry about the value is changed in 1 method may affect another method.因此您不必担心在 1 个方法中更改值可能会影响另一个方法。

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

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