C#学习教程:在为属性创建委托时无法绑定到目标方法属性值提高性能。代码:Properties=type.GetProperties(BindingFlags.Public|BindingFlags.Instance).Where(p=>p.CanRead&&!p.GetIndexParameters().Any()).AsEnumerable();PropertyGetters=Properties.ToDictionary(p=>p.Name,p=>(Func)Delegate.CreateDelegate(typeof(Func),p.GetGetMethod()));PropertySetters=Properties.Where(p=>p.GetSetMethod()!=null).ToDictionary(p=>p.Name,p=>(Action)Delegate.CreateDelegate(typeof(Action),p.GetSetMethod()));但是我得到以下异常:无法绑定到目标方法,因为它的签名或安全透明度不同于委托类型的签名或安全透明度不兼容。据我所知,这可能是由静态/索引/值类型属性引起的,Properties集合不包含静态或索引属性,但对于值类型属性(如int和double)我确实需要它。如何在保持代码抽象并避免泛型的同时创建我需要的getter/setter?好的,终于找到了这个问题的答案:MethodInfo.Invokeperformanceissues更具体地说,这篇文章:ReflectingonFlyingandExploringRepresentations这是我最终得到的代码的要点:publicclassHelper{privateIDictionary>PropertyGetters{get;放;}privateIDictionary>PropertySetters{get;放;}publicstaticFuncCreateGetter(PropertyInfoproperty){if(property==null)thrownewArgumentNullException("property");vargetter=property.GetGetMethod();if(getter==null)thrownewArgumentException("指定的属性没有公共访问器。");vargenericMethod=typeof(Helper).GetMethod("CreateGetterGeneric");MethodInfogenericHelper=genericMethod.MakeGenericMethod(property.DeclaringType,property.PropertyType);返回(Func)genericHelper.Invoke(null,newobject[]{getter});}publicstaticFuncCreateGetterGeneric(MethodInfogetter)whereT:class{FuncgetterTypedDelegate=(Func)Delegate.CreateDelegate(typeof(Func),getter);FuncgetterDelegate=(Func)((对象实例)=>getterTypedDelegate((T)实例));返回getterDelegate;}publicstaticActionCreateSetter(PropertyInfoproperty){if(property==null)thrownewArgumentNullException("property");varsetter=property.GetSetMethod();if(setter==null)thrownewArgumentException("指定的属性没有公共setter。");vargenericMethod=typeof(Helper).GetMethod("CreateSetterGeneric");MethodInfogenericHelper=genericMethod.MakeGenericMethod(property.DeclaringType,property.PropertyType);返回(Action)genericHelper.Invoke(null,newobject[]{setter});}publicstaticActionCreateSetterGeneric(MethodInfosetter)whereT:class{ActionsetterTypedDelegate=(Action)Delegate.CreateDelegate(typeof(Action),setter);动作setterDelegate=(Action)((objectinstance,objectvalue)=>{setterTypedDelegate((T)instance,(V)value);});返回setterDelegate;}publicHelper(类型类型){varProperties=type.GetProperties(BindingFlags.Public|BindingFlags.Instance).Where(p=>p.CanRead&&!p.GetIndexParameters().Any()).AsEnumerable();PropertyGetters=Properties.ToDictionary(p=>p.Name,p=>CreateGetter(p));PropertySetters=Properties.Where(p=>p.GetSetMethod()!=null).ToDictionary(p=>p.Name,p=>CreateSetter(p));}}generateddelegate平均而言,它看起来比使用反射快80%,所以我对结果非常满意!我遇到了与我使用ExpressionsAPI解决此问题时相同的错误。注意:要引用的方法是委托名称为Formula,其签名如下publicdelegatefloatFormula(Dictionarycr,List>allr);获取将被引用为DelegateAssemblyassembly=results.CompiledAssembly;的MethodInfovargeneratedType=assembly.GetType("First.NewClass");vargeneratedMethod=generatedType.GetMethod("公式方法");准备代理作为参数表达式的参数。参数一:字典参数二:List>vararg1Expression=Expression.Parameter(typeof(Dictionary));vararg2Expression=Expression.Parameter(typeof(List>));生成最终方法CallExpression并返回Delegate。以上是C#学习教程:为属性创建委托时,不能绑定到目标方法共享所有内容。如果对大家有用,需要进一步了解C#学习教程,希望大家多多关注——varmethodCall=Expression.Call(generatedMethod,arg1Expression,arg2Expression);返回Expression.Lambda(methodCall,arg1Expression,arg2Expression).Compile();本文收集自网络,不代表立场。如涉及侵权,请点击右侧联系管理员删除。如需转载请注明出处:
