【发布时间】:2010-11-08 18:37:21
【问题描述】:
编辑:我已将结果写成blog post。
C# 编译器对 COM 类型的处理有点神奇。比如这个语句看起来很正常……
Word.Application app = new Word.Application();
...直到您意识到Application 是一个接口。在接口上调用构造函数?呸!这实际上被转化为对Type.GetTypeFromCLSID() 的调用和对Activator.CreateInstance 的调用。
另外,在 C# 4 中,您可以对ref 参数使用非引用参数,编译器只需添加一个局部变量以通过引用传递,丢弃结果:
// FileName parameter is *really* a ref parameter
app.ActiveDocument.SaveAs(FileName: "test.doc");
(是的,缺少一堆参数。可选参数不是很好吗?:)
我正在尝试调查编译器行为,但我未能伪造第一部分。我可以毫无问题地完成第二部分:
using System;
using System.Runtime.InteropServices;
using System.Runtime.CompilerServices;
[ComImport, GuidAttribute("00012345-0000-0000-0000-000000000011")]
public interface Dummy
{
void Foo(ref int x);
}
class Test
{
static void Main()
{
Dummy dummy = null;
dummy.Foo(10);
}
}
我希望能够写作:
Dummy dummy = new Dummy();
虽然。显然它会在执行时爆炸,但这没关系。我只是在做实验。
编译器为链接的 COM PIA(CompilerGenerated 和 TypeIdentifier)添加的其他属性似乎不起作用...什么是神奇的酱汁?
【问题讨论】:
-
可选参数不是很好吗? IMO,不,他们不好。微软正试图通过向 C# 添加膨胀来修复 Office COM 接口中的缺陷。
-
@Mehrdad:当然,可选参数在 COM 之外很有用。您需要注意默认值,但在它们和命名参数之间,构建可用的不可变类型要容易得多。
-
是的。具体来说,命名参数可能是实际上需要与某些动态环境进行互操作的。当然,毫无疑问,这是一个有用的功能,但这并不意味着它是免费的。它以简单为代价(明确规定的设计目标)。就个人而言,我认为 C# 对于团队遗漏的功能来说是惊人的(否则,它可能是 C++ 的克隆)。 C# 团队很棒,但企业环境很难没有政治。我猜安德斯本人对此并不十分高兴,正如他在 PDC'08 演讲中所说:“我们花了十年时间才回到原来的位置。”
-
我同意团队需要密切关注复杂性。动态的东西增加了很多复杂性,对于大多数开发者来说价值不大,但对于一些开发者来说价值很高。
-
我已经看到框架开发人员开始在很多地方讨论它的用途。 IMO 是时候找到
dynamic的好用处了……我们太习惯于静态/强类型,不知道为什么它在 COM 之外很重要。
标签: c# com compiler-construction c#-4.0