输出类型仅在运行时已知的泛型参数
本文关键字:泛型 参数 运行时 类型 输出 | 更新日期: 2023-09-27 18:02:45
有一个接口:
public interface IOut<T>
{
void Get(out T output);
}
和实现它的类:
public class Impl : IOut<string>, IOut<int>{
public void Get(out string output) { output = "string"; }
public void Get(out int output) { output = 12; }
}
我可以这样做:
public static void Main()
{
dynamic dImpl = new Impl();
string sOutput;
int iOutput;
dImpl.Get(out sOutput);
dImpl.Get(out iOutput);
Console.WriteLine(sOutput);
Console.WriteLine(iOutput);
}
我的问题是,我只知道在运行时我需要获取的类型,所以我希望如何调用我的Get
代码是这样的:
public static void Main()
{
dynamic dImpl = new Impl();
var t = typeof(string);
t output;
dImpl.Get(out output);
Console.WriteLine(output);
}
现在,我知道这个不会起作用,我已经尝试了反射性地执行Cast:
public static T Cast<T>(object o) { return (T) o; }
但是我没有对象要强制转换,我只有一个Type
。默认值:
public static T Default<T>() { return default(T); }
,但默认的东西,如string
等是空的,当调用方法通过反射:
var method = typeof(Program).GetMethod("Default").MakeGenericMethod(typeof(string));
var defaulted = method.Invoke(null, null);
defaulted
将为空,当调用dImpl.Get(out defaulted)
时,运行时不确定使用哪个过载。
所以,我要找的是:A)以某种方式使用当前的接口设置来做到这一点[首选]B)实现目标的不同方式
您可以从接口类型而不是实现类型中获得要调用的方法:
object[] parameters = new object[] { null };
Type typeParam = typeof(string);
Type ifaceType = typeof(IOut<>).MakeGenericType(typeParam);
MethodInfo method = ifaceType.GetMethod("Get");
var impl = new Impl();
method.Invoke(impl, parameters);
object outParam = parameters[0];
如果你在运行时才知道output
的类型,你就不能在c#中声明它的强类型实例。
如果你可以使调用逻辑(Main
在你的例子中)在T
上也是通用的,那将工作-但这只是推迟你的问题。
另一个选择是将output
声明为基类或接口,并将泛型T
限制为基类或接口。使用object
作为基类可能对你有用——这取决于你想用它做什么。