c#如何通过泛型动态返回实例

本文关键字:返回 实例 动态 泛型 何通过 | 更新日期: 2023-09-27 18:15:34

查看我的代码

class Program
{
    static void Main(string[] args)
    {
        Employee T = GetInstance<Importance.Employee>(Importance.Employee);
    }
    public static T GetInstance<T>(Importance objType)
    {
        if (objType == Importance.Employee)
            return (T)Convert.ChangeType((new Employee()), typeof(T));
        else 
            return (T)Convert.ChangeType((new Teacher()), typeof(T));
    }
}
public class Employee
{
    string ID = "";
    string Name = "";
}
public class Teacher
{
    string ID = "";
    string Name = "";
}
enum Importance
{
    Employee,
    Teacher
};

这一行不工作:

Employee emp = GetInstance<Importance.Employee>(Importance.Employee);

抛出错误

GenericFunction.Importance。"雇员"是一个"字段",但像"类型"一样使用

我犯错误的地方。请帮助,因为我正在努力学习通用,因为我弱那里。由于

c#如何通过泛型动态返回实例

正如Gilad Green所说,您将value用作type。你可以这样做:

class Program
{
    static void Main(string[] args)
    {
        Employee employee = GetInstance<Employee>(Importance.Employee);
        Teacher teacher = GetInstance<Teacher>(Importance.Teacher);
        Console.WriteLine(employee.GetType());
        Console.WriteLine(teacher.GetType());
        Console.ReadKey();
    }
    public static T GetInstance<T>(Importance objType)
    {
        if (objType == Importance.Employee)
            return (T)Convert.ChangeType((new Employee()), typeof(T));
        else
            return (T)Convert.ChangeType((new Teacher()), typeof(T));
    }
}
public class Employee
{
    string ID = "";
    string Name = "";
}
public class Teacher
{
    string ID = "";
    string Name = "";
}
enum Importance
{
    Employee,
    Teacher
};

但是,正如我所看到的,如果您只想要给定类型的新对象,则此处不需要重要性枚举。你可以这样做:

class Program
{
    static void Main(string[] args)
    {
        Employee employee = GetInstance<Employee>();
        Teacher teacher = GetInstance<Teacher>();
        Console.WriteLine(employee.GetType());
        Console.WriteLine(teacher.GetType());
        Console.ReadKey();
    }
    public static T GetInstance<T>() where T : class, new()
    {
        return new T();
    }
}
public class Employee
{
    string ID = "";
    string Name = "";
}
public class Teacher
{
    string ID = "";
    string Name = "";
}

我们可以再考虑一下,给出两个样本。一个带Enum,一个带多态。

如果你真的想保持与Enum,那么我认为你的泛型类型与Enum参数只服务于确保它不会返回不同的类型,所以它将是类似的:

class Program
{
    static void Main(string[] args)
    {
        var employee = GetInstance<Employee>(Importance.Employee);
        var teacher = GetInstance<Teacher>(Importance.Teacher);
        Console.WriteLine(employee.GetType());
        Console.WriteLine(teacher.GetType());
        Console.ReadKey();
    }
    public static T GetInstance<T>(Importance importance) where T : Role, new()
    {
        if (typeof(T) == typeof(Employee) && importance != Importance.Employee)
        {
            throw new InvalidCastException();
        }
        if (typeof(T) == typeof(Teacher) && importance != Importance.Teacher)
        {
            throw new InvalidCastException();
        }
        return new T();
    }
}
public abstract class Role { }
public class Employee : Role
{
    string ID = "";
    string Name = "";
}
public class Teacher : Role
{
    string ID = "";
    string Name = "";
}
public enum Importance
{
    Teacher,
    Employee
}

但是我不认为这有意义。我会这样做:

class Program
{
    static void Main(string[] args)
    {
        var employee = GetInstance<Employee>();
        var teacher = GetInstance<Teacher>();
        Console.WriteLine(employee.GetType());
        Console.WriteLine(teacher.GetType());
        Console.ReadKey();
    }
    public static T GetInstance<T>() where T : Role, new()
    {
        var role = new T();
        // do something important here
        return role;
    }
}
public abstract class Role { }
public class Employee : Role
{
    string ID = "";
    string Name = "";
}
public class Teacher : Role
{
    string ID = "";
    string Name = "";
}

当像这样使用它时,您实际上是用Employee的值来处理Importance的enum -这不是类型,而是值。

不要这样定义方法,添加一个Role基类:

public class Role
{
    public string Id { get; set; }
    public string Name { get; set; }
}
public class Employee : Role
{
}
public class Teacher : Role
{
}

方法:

public static Role GetInstance(Importance objType)
{
    if (objType == Importance.Employee)
        return new Employee();
    else
        return new Teacher();
}

这基本上是Factory设计模式


在您的场景中,使用泛型方法然后传递enum值来确定要实例化的类型是没有意义的。此外,在当前的实现中,如果将T传递为TeacherImportance.Employee值:

var obj = Convert.ChangeType((new Employee()), typeof(Teacher));

你将得到:

InvalidCastException - Object必须实现IConvertible

决定你想做什么。如果您想要一个像enum(和上面的例子)这样的映射值,或者一个获得T类型实例化的泛型函数:

public static TRole GetInstance<TRole>() where TRole : Role, new()
{
    return new TRole();
}
Employee T = GetInstance<Employee>();