Kum*_*mar 7 .net c# outlook interop com-interop
尝试为POCO创建一个Microsoft Office对象的映射器并找到它
// doesn't work
// returns an empty array where o is a RCW on an office object
foreach(var pi in o.GetType().GetProperties() )
tgt.SetValue(rc, pi.GetValue(o, null));
Run Code Online (Sandbox Code Playgroud)
所以不得不求助于此
foreach(var field in tgt.GetFields() ){
var pv = o.InvokeMember(field.Name, System.Reflection.BindingFlags.GetProperty, null, o, null);
i.SetValue(rc, pv);
}
Run Code Online (Sandbox Code Playgroud)
它现在有效,但想知道为什么RCW.GetProperties()这里不起作用?
pho*_*oog 18
在撰写本文时,另外两个答案是正确的,但它们错过了一个重要的机会来解释COM对象的后期绑定在.NET类型系统方面的外观. 当您调用GetTypeCOM对象时,返回值是__ComObject内部类型,而不是您在编写互操作代码时通常使用的COM接口类型. 您可以在调试器中看到这个,或者使用某些代码Console.WriteLine(o.GetType().Name);.
该__ComObject类型没有属性; 这就是你打电话时得到一个空数组的原因o.GetType().GetProperties().(至少生活中的一些事情是有意义的!)
如果您反编译该InvokeMember方法,您会发现它对COM对象有特殊处理,将调用委托给内部本机方法.对于"常规".NET对象,该方法使用"常规".NET反射,检索适用MemberInfo于请求的成员并调用它.
您可以在接口类型上使用.NET反射.例如,如果您知道该对象是Excel Worksheet,则可以使用typeof(Worksheet).GetProperties(),并将结果PropertyInfo实例与对象一起使用.但是,如果在编译时不知道对象的类型,则需要调用GetType(),如示例代码中所示.在那种情况下,你坚持使用InvokeMember.
这是因为最近绑定了 COM 对象。运行时不知道 COM 对象上有哪些方法/属性可用,直到它们被访问/调用。
这里有一些关于这个主题的好文章:
http://support.microsoft.com/default.aspx?scid=kb;en-us;Q302902
http://www.codeproject.com/Articles/10838/How-To-Get-Properties-and-Methods-in-Late-Binding