c# - IDynamicMetaObjectProvider set property using literal name -
i need set dynamicobject property using string propertyname. found way property value using answer, when comes setvalue i'm not quite sure how rewrite code in order set property. receive runtime errors , not quite sure expressions logic. wonder if can suggest idea how implement void setproperty(object o, string member,object value) method.
in cases expandoobject, can use idictionary<string,object> api instead:
expandoobject obj = ... var dict = (idictionary<string, object>)obj; object oldval = dict[membername]; dict[membername] = newval; in more general case of idynamicmetaobjectprovider: borrow callsitecache fastmember:
internal static class callsitecache { private static readonly hashtable getters = new hashtable(), setters = new hashtable(); internal static object getvalue(string name, object target) { callsite<func<callsite, object, object>> callsite = (callsite<func<callsite, object, object>>)getters[name]; if (callsite == null) { lock (getters) { callsite = (callsite<func<callsite, object, object>>)getters[name]; if (callsite == null) { callsite<func<callsite, object, object>> newsite = callsite<func<callsite, object, object>>.create(binder.getmember(csharpbinderflags.none, name, typeof(callsitecache), new csharpargumentinfo[] { csharpargumentinfo.create(csharpargumentinfoflags.none, null) })); getters[name] = callsite = newsite; } } } return callsite.target(callsite, target); } internal static void setvalue(string name, object target, object value) { callsite<func<callsite, object, object, object>> callsite = (callsite<func<callsite, object, object, object>>)setters[name]; if (callsite == null) { lock (setters) { callsite = (callsite<func<callsite, object, object, object>>)setters[name]; if (callsite == null) { callsite<func<callsite, object, object, object>> newsite = callsite<func<callsite, object, object, object>>.create(binder.setmember(csharpbinderflags.none, name, typeof(callsitecache), new csharpargumentinfo[] { csharpargumentinfo.create(csharpargumentinfoflags.none, null), csharpargumentinfo.create(csharpargumentinfoflags.usecompiletimetype, null) })); setters[name] = callsite = newsite; } } } callsite.target(callsite, target, value); } } note here could type target idynamicmetaobjectprovider, don't need - callsite api doesn't require it.
Comments
Post a Comment