编辑:基于LoveMeSomeCode的答案,我相信这个问题只出现在VB.Net中。使用反射设置属性值为Nothing(空)
我想通过在字典中保存已更改属性的旧值并在需要恢复时通过反射设置它们来将类恢复为以前的状态。我有一个问题,如果旧值是Nothing(null)当我尝试设置属性时,我得到一个空引用异常。这是我尝试过的。
假设每个循环是这样的:
For Each pair As KeyValuePair(Of String, Object) In myOldValues
...
Next
方法1:
CallByName(Me, pair.Key, CallType.Set, pair.Value)
方法2:
Me.GetType().InvokeMember(pair.Key, Reflection.BindingFlags.SetProperty, Nothing, Me, pair.Value)
方法3:
Dim propInfo As System.Reflection.PropertyInfo = Me.GetType.GetProperty(pair.Key)
propInfo.SetValue(Me, Convert.ChangeType(pair.Value, propInfo.PropertyType), Nothing)
对于这些方法中的每一个,当pair.Value为null时,我会得到一个空引用异常。 setter能够保存一个空值(通常该属性是一个字符串)。我做错了什么,或者我该如何解决它?
编辑:如果我直接传递null,每个方法都会失败。
编辑:这里是堆栈跟踪,如果他们帮助别人:
方法1 System.NullReferenceException:对象不设置到对象的实例。 at Microsoft.VisualBasic.CompilerServices.Symbols.Container.InvokeMethod(Method TargetProcedure,Object [] Arguments,Boolean [] CopyBack,BindingFlags Flags) at Microsoft.VisualBasic.CompilerServices.NewLateBinding.LateSet(Object Instance,Type Type,String MemberName ,Object []参数,String [] ArgumentNames,Type [] TypeArguments,布尔OptimisticSet,布尔RValueBase,CallType CallType)在Microsoft.VisualBasic.CompilerServices.Versioned.CallByName(对象实例,字符串MethodName,CallType UseCallType,Object []参数 参数) 在MYFILEmyProject的 .Presenter.CustomerDetailPresenter.RevertCustomer():线378
方法2 System.Reflection.TargetInvocationException:调用的目标引发了异常。 ---> System.NullReferenceException:未将对象引用设置为对象的实例。 在myProject的 .Presenter.CustomerDetailPresenter.set_City(字符串值) ---内部异常堆栈跟踪的结尾--- 在System.RuntimeMethodHandle._InvokeMethodFast(对象目标,对象[]参数,SignatureStruct & SIG,MethodAttributes methodAttributes ,运行时类型句柄typeOwner) at System.RuntimeMethodHandle.InvokeMethodFast(Object object,Object [] arguments,Signature sig,MethodAttributes methodAttributes,RuntimeTypeHandle typeOwner) at System.Reflection.RuntimeMethodInfo.Invoke(Object obj,BindingFlags invokeAttr,Binder binder,Object [ ]参数,CultureInfo文化,布尔skipVisibilityChecks) 在System.Reflection.RuntimeMethodInfo。Invoke(Object obj,BindingFlags invokeAttr,Binder binder,Object []参数,CultureInfo culture) at System.RuntimeType.InvokeMember(String name,BindingFlags bindingFlags,Binder binder,Object target,Object [] providedArgs,ParameterModifier []修饰符,CultureInfo培养,字符串[] namedParams) 在System.Type.InvokeMember(字符串名称,的BindingFlags invokeAttr,粘结剂粘结剂,对象目标,在myProject的 .Presenter.CustomerDetailPresenter.RevertCustomer()
对象[]参数) 方法3 System.Reflection.TargetInvocationException:调用的目标引发了异常。 ---> System.NullReferenceException:未将对象引用设置为对象的实例。 在myProject的 .Presenter.CustomerDetailPresenter.set_City(字符串值) ---内部异常堆栈跟踪的结尾--- 在System.RuntimeMethodHandle._InvokeMethodFast(对象目标,对象[]参数,SignatureStruct & SIG,MethodAttributes methodAttributes ,运行时类型句柄typeOwner) at System.RuntimeMethodHandle.InvokeMethodFast(Object object,Object [] arguments,Signature sig,MethodAttributes methodAttributes,RuntimeTypeHandle typeOwner) at System.Reflection.RuntimeMethodInfo.Invoke(Object obj,BindingFlags invokeAttr,Binder binder,Object [ ]参数,CultureInfo culture,布尔skipVisibilityChecks)
at System.Ref lection.RuntimeMethodInfo.Invoke(Object obj,BindingFlags invokeAttr,Binder binder,Object []参数,CultureInfo culture) at System.RuntimeType.InvokeMember(String name,BindingFlags bindingFlags,Binder binder,Object target,Object [] providedArgs,ParameterModifier [ ]改性剂,CultureInfo的文化,字符串[] namedParams) 在System.Type.InvokeMember(字符串名称,的BindingFlags invokeAttr,粘结剂粘结剂,目标对象,对象[]参数) 在myProject的 .Presenter.CustomerDetailPresenter.RevertCustomer()
你确定PropertyInfo.SetValue是抛出异常的方法吗? – jason 2009-01-23 00:14:00
这或它的一个子方法,就是这一行。 – 2009-01-23 01:22:27
检查异常堆栈跟踪;你应该能够辨别出抛出异常的方法。如果你无法弄清楚,请尝试单独调用Convert.ChangeType。我怀疑是该方法抛出异常。 – jason 2009-01-23 01:31:59