我在将对象强制转换为生活在另一个库中的其中一个基础接口时遇到了问题。下面是它的代码:将对象强制转换为基础接口
BaseSDK.dll
public interface IPlugin
{
void Run();
}
CustomPlugin.Definition.dll:
public interface ICustomPlugin
{
void DoCustomStuff();
}
CustomPlugin.dll(具有参照BaseSDK.dll和CustomPlugin.Definition.dll):
public class CustomPlugin: IPlugin, ICustomPlugin
{
public void Run()
{
}
public void DoCustomStuff()
{
}
}
Host.exe(有BaseSDK.dll和CustomPlugin.Definition.dll引用):
IPlugin plugin;
public void DoStuff()
{
plugin = LoadPluginAndCreateAnInstanceSomehow();
// I know plugin is a CustomPlugin
ICustomPlugin customPlugin = plugin as ICustomPlugin; //cast fails.
customPlugin.DoCustomStuff();
}
我不明白;这只是简单的将类型转换为基本类型。我怎样才能解决这个问题?或任何替代品?
编辑:这里是什么LoadPluginAndCreateAnInstanceSomehow()
做了总结:
Assembly ass = Assembly.LoadFrom(filename);
Type t = ass.GetType(ass.FullName + ".CustomPlugin");
plugin = (IPlugin)Activator.CreateInstance(t);
编辑2:插件加载到另一个AppDomain中。我不得不在编译时添加IPlugin和ICustomPlugin.Definiton作为参考,因为应用程序必须知道CustomPlugin是什么样的。这是问题的根源吗?如果是这样,我该如何实现我想要做的?
编辑3:插件加载这样的:
public class PluginLoader
{
List<IPlugin> Plugins;
AppDomain Domain;
string libPath;
public void PluginLoader(string sLibPath, AppDomain sDomain)
{
libPath = sLibPath;
Plugins = new List<IPlugin>();
Domain = sDomain;
if(Domain==null)Domain = AppDomain.CreateDomain("PluginsDomain");
Domain.AssemblyResolve += new ResolveEventHandler(Domain_AssemblyResolve);
Domain.TypeResolve += new ResolveEventHandler(Domain_TypeResolve);
Domain.DoCallBack(new CrossAppDomainDelegate(DomainCallback));
}
Assembly Domain_AssemblyResolve(object sender, ResolveEventArgs args)
{
return Assembly.LoadFrom(args.Name);
}
Assembly Domain_TypeResolve(object sender, ResolveEventArgs args)
{
return Assembly.LoadFrom(args.Name);
}
void DomainCallback()
{
string[] fileNames = Directory.GetFiles(libPath, "*.dll");
foreach (string filename in fileNames)
{
FileInfo fi = new FileInfo(filename);
Assembly ass = Assembly.LoadFrom(fi.FullName);
Type t = ass.GetType(ass.FullName + ".CustomPlugin");
IPlugin p = (IPlugin)Activator.CreateInstance(t);
Plugins.Add(p);
}
}
}
你能告诉我们你是如何加载到另一个AppDomain插件?我已经尝试过在各种不同地点的DLL,但我不能复制你的问题。 – Sam 2010-08-18 02:19:36
Assembly ass = Assembly.LoadFrom(fi.FullName)。大声笑在变量名称。 – obelix 2010-08-18 03:24:15
我很困惑。为什么有人预期从不同应用程序域加载的类型将与当前应用程序域中加载的相同类型兼容? – 2010-08-18 03:28:21