zoukankan      html  css  js  c++  java
  • 反射给对象赋值遇到的问题——类型转换【转】

     

    转自http://blog.csdn.net/xiaohan2826/article/details/8536074

    给一个对象属性赋值可以通过PropertyInfo.SetValue()方式进行赋值,但要注意值的类型要与属性保持一致。  

    创建对象实例的两种方法: 

    1.

    1
    var obj = Assembly.Load("AssemblyName").CreateInstance("AssemblyName"+"ClassFullName");

    2.

    1
    var obj = Activator.CreateInstance(ClassType);

    以后有时间再把这两种的区别详细讲一下。

    创建好实例时,现在可以给当前实例的某个属性赋值,首先获取要赋值的属性。

    1
    var property = obj.GetType().GetProperty("PropertyName");//此时可以使用GetProperty获取属性数组,循环进行赋值,这里主要讲解类型问题。

    赋值可通过PropertyInfo.SetValue()方法,详见MSDN。

    情况1,该属性类型是已知类型,例如:int

    1
    2
    int value=500;
    property.SetValue(obj,value,null);

    这里需要注意value值的类型必须和属性类型一致,否则会抛出TargetException异常。

    情况2,该属性类型是已知类型,原值是其他类型。例如:目标类型为int,值为string

    1
    2
    string value="500";
    property.SetValue(obj,int.TryParse(value),null);//类型转换。

    前两种情况都很简单,有时业务会比较复杂,对目标类型不确定,需要程序运行时判断。

    情况3,该属性类型是未知非泛型类型,不确定目标类型,如何进行类型转换。

    1
    2
    object value="500";
    property.SetValue(obj,Convert.ChangeType(value,property.PropertyType),null);//类型转换。

    这样就可以解决大多数问题了。

    不知道大家有没有注意,我在第三种情况强调了非泛型,难道泛型就不行了吗? 是的。如果只是用Convert.ChangeType()方法,类型转换仍然报错,即使目标类型和值的类型是一致,通过Convert.ChangeType()进行转换仍然报错。
    解决这个问题,就要先把属性值类型转成基类型后,在进行Convert转换

    if (!property.PropertyType.IsGenericType)
     
                {
     
                    //非泛型
     
                    property.SetValue(obj, string.IsNullOrEmpty(value) ? null : Convert.ChangeType(value, property.PropertyType), null);
     
                }
     
                else
     
                {
     
                    //泛型Nullable<>
     
                    Type genericTypeDefinition = property.PropertyType.GetGenericTypeDefinition();
     
                    if (genericTypeDefinition == typeof(Nullable<>))
     
                    {
     
                        property.SetValue(obj, string.IsNullOrEmpty(value) ? null : Convert.ChangeType(value, Nullable.GetUnderlyingType(property.PropertyType)), null);
     
                    }
     
                }
    

      

    本博客文章皆出于学习目的,个人总结或摘抄整理自网络。引用参考部分在文章中都有原文链接,如疏忽未给出请联系本人。另外,作为一名菜鸟程序媛,如文章内容有错误,欢迎点击博客右上方的扣扣链接指导交流。
  • 相关阅读:
    Linkerd 2.10(Step by Step)—将 GitOps 与 Linkerd 和 Argo CD 结合使用
    Linkerd 2.10(Step by Step)—多集群通信
    Linkerd 2.10(Step by Step)—使用 Kustomize 自定义 Linkerd 的配置
    Linkerd 2.10(Step by Step)—控制平面调试端点
    Linkerd 2.10(Step by Step)—配置超时
    Linkerd 2.10(Step by Step)—配置重试
    Linkerd 2.10(Step by Step)—配置代理并发
    本地正常运行,线上环境诡异异常原因集合
    Need to invoke method 'xxx' declared on target class 'yyy', but not found in any interface(s) of the exposed proxy type
    alpine 安装常用命令
  • 原文地址:https://www.cnblogs.com/goingforward/p/5104979.html
Copyright © 2011-2022 走看看