微信公众号搜"智元新知"关注
微信扫一扫可直接关注哦!

C#通过反射将派生类转换为基类异常

我有一个应用程序使用反射动态创建类.部署时,将派生类转换为基类时会得到异常.它只发生在100台机器中.所有的类都在同一个程序集中.以下是一些代码片段,并且在发生异常之前的日志消息中输出.我在我的智慧结局,任何帮助非常感谢.
//Parent class
namespace Framework.DataModel
{
    [Serializable]
    public class DataTreeRequest : TreeNode,IDirtyListener,ISerializable
    {
        ....
    }
}

// Derived Class    
namespace Framework.DataModel
{
    [Serializable]
    public class CADElementRequest : DataTreeRequest
    {
        public CADElementRequest(String name) : base(name){}
    }
}


// Method that uses reflection to create class and then cast to its base class
namespace Framework.DataModel
{
    [Serializable]
    public class DataModelBuilder : CoreBuilder
    {
        ...

        protected DataTreeRequest CreateDataTreeRequest(String asmName,String inName,String inType,String inSourceName)
        {
            DataTreeRequest dtr = null;

            Assembly asm = Assembly.LoadFrom(asmName);
            if (asm == null)
            {
                throw new BaseException("Can't find assembly " + asmName);
            }

            Type requestType = asm.GetType(inType);
            if (requestType == null)
            {
                throw new BaseException("Can't find class of type " + inType + " in assembly " + asmName);
            }

            // Call the constructor for the tree node that takes the xml node as an argument
            Type[] constructorArgsTypes = new Type[1];
            constructorArgsTypes[0] = typeof(String);
            ConstructorInfo constructorInfo = requestType.GetConstructor(constructorArgsTypes);
            if (constructorInfo == null)
            {
                throw new BaseException("Can't find constructor for type " + inType + " that takes a String param");
            }

            Object[] constructorArgs = new Object[1];
            constructorArgs[0] = inName;
            Object newObj = constructorInfo.Invoke(constructorArgs);

            // Code fails on this line trying to cast derived class to base class on 1 in 100 machines
            dtr = newObj as DataTreeRequest;
            if (dtr == null)
            {
                throw new BaseException("Can't cast newObj to type DataTreeRequest. newObj = " + newObj + ",Type = " + newObj.GetType().ToString());
            }

            dtr.InSource = inSourceName;

            return dtr;
        }
    }
}

在失败的机器上记录输出

Message = Found assembly=Framework.DataModel,Version=1.0.5885.31486,
Culture=neutral,PublicKeyToken=null

Message = newObj
AssemblyQualifiedname=Framework.DataModel.CADElementRequest,
Framework.DataModel,Culture=neutral,
PublicKeyToken=null,BaseType==Framework.DataModel.DataTreeRequest,
FullName==Framework.DataModel.CADElementRequest

BaseException: Can’t cast newObj to type DataTreeRequest. newObj =
Name=Substations;InType=;InName=Substations;OutName=Substations;InSource=;OutSource=;,
Type = Framework.DataModel.CADElementRequest

解决方法

尝试更换
Assembly asm = Assembly.LoadFrom(asmName);
if (asm == null)
{
    throw new BaseException("Can't find assembly " + asmName);
}

Type requestType = asm.GetType(inType);

Type requestType = Type.GetType(inType)

其中inType是程序集合的名称
https://msdn.microsoft.com/en-us/library/system.type.assemblyqualifiedname(v=vs.110).aspx

如果您需要项目未引用的加载程序集考虑使用Assembly.Load方法.

关于使用Assembly.LoadFrom的缺点,请参阅https://msdn.microsoft.com/EN-US/library/1009fa28(v=VS.110,d=hv.2).aspx中的“备注”部分

原文地址:https://www.jb51.cc/csharp/93360.html

版权声明:本文内容由互联网用户自发贡献,该文观点与技术仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 dio@foxmail.com 举报,一经查实,本站将立刻删除。

相关推荐