c#泛型方法和将对象作为参数的方法有什么区别?

时间:2018-11-13 02:27:22

标签: c#

static void Swap<T>(ref T var1, ref T var2)
{
    T temp = var1;
    var1 = var2;
    var2 = temp;
}

static void Swap2(ref object var1, ref object var2)
{
    object temp = var1;
    var1 = var2;
    var2 = temp;
}

我认为Swap在某种程度上优于Swap2?

1 个答案:

答案 0 :(得分:-1)

这个问题已经被回答了很多次,所以如果这个投票被关闭,不要感到惊讶。

在您的示例中,由于方法无效,并且它们只是相互引用,因此没有区别。然而;如果您添加了Swap<T>

,则可以使用where T : {the base type to filter against}过滤基本类型

由于多种原因,泛型通常比使用对象要好,但排名第一的应该是装箱/拆箱。 (在您的示例中没有发生。)

使用object时,必须将其强制转换为预期使用的类型。这导致大量的开销和潜在的错误。使用泛型时,您具有编译时类型,因此可以在编译之前或编译过程中捕获许多异常,可以使用更强大的类型,最重要的是,您不应进行装箱/拆箱处理(这会降低性能)。

要考虑的另一件事是,在示例中使用Swap<T>时,由于Type不能同时是不同类型,因此您将两者强制设为相同的T 。使用Swap2,您可以重新引用任意两个对象。但是,您将必须手动将这些类型转换为对象,并且它们不能返回其原始类型,因为除非两者以相同的类型开头。

记住ref参数不会从多态中受益。 T参数是通用的,但由于我们只有一个T,所以类型将始终相同。

using System;

namespace Question_Answer_Console_App
{
    class Program
    {

        static void Main(string[] args)
        {
            var text = "Hey There";
            var employer1 = new Employer() { Name = "Microsoft" };
            var employer2 = new Employer() { Name = "EA Games" };

            //Generic Swap
            SwapGeneric(ref employer1, ref employer2);
            //Swap(ref text, ref employee2); //<- compiler error. Cannot be inferred by the usage.

            Console.WriteLine("Types of the same swapped");
            Console.WriteLine(employer1.Name);
            Console.WriteLine(employer2.Name);
            Console.WriteLine();
            //object Swap
            //SwapObject(ref employee1, ref employee2); //- compiler error.  Cannot convert to ref object.

            //Reference string and employer as object.
            var textObject = text as object;
            var employerObject = employer1 as object;

            SwapObject(ref textObject, ref employerObject);

            //Existing types cannot be re-referenced.
            //text = (Employer)textObject; //<-compiler error.  Cannot implicitly convert...
            //employer1 = (string)employerObject; //<-compiler error. Cannot implicitly convert....

            //We can cast objects to swapped types succesfully but see how easily this can cause error and confusion.
            Console.WriteLine("Objects of different types swapped");
            Console.WriteLine(((Employer)textObject).Name);
            Console.WriteLine((string)employerObject);

            Console.ReadKey();
        }

        static void SwapGeneric<T>(ref T var1, ref T var2)
        {
            T temp = var1;
            var1 = var2;
            var2 = temp;
        }

        static void SwapObject(ref object var1, ref object var2)
        {
            object temp = var1;
            var1 = var2;
            var2 = temp;
        }
    }

    public class Employer
    {
        public object Name { get; set; }
    }
}
//OUTPUT
//Types Swapped
//EA Games
//Microsoft

//Objects Swapped
//EA Games
//Hey There