为什么我不应该使用 AutoDual?

发布于 2024-08-29 23:00:43 字数 199 浏览 4 评论 0原文

到目前为止,我一直使用 [AutoDual] 属性来装饰我想在 VB6 中使用的 .NET 类。重点是在 VB6 环境中获得对 .NET 对象的智能感知。然而,有一天我用谷歌搜索 AutoDual,第一个答案是“不要使用 AutoDual”。

我一直在寻找为什么我不应该使用它的连贯解释,但找不到它。

这里有人可以解释一下吗?

Up to now, I've always decorated my .NET classes that I want to use from VB6 with the [AutoDual] attribute. The point was to gain Intellisense on .NET objects in the VB6 environment. However, the other day I googled AutoDual and the first answer is 'Do Not Use AutoDual'.

I've looked for coherent explanation of why I shouldn't use it, but could not find it.

Can someone here explain it?

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(2

只有一腔孤勇 2024-09-05 23:00:43

我找到了一种可靠的方法,可以为 VB6 中的 .NET 对象提供智能感知,同时又不会破坏接口。关键是用DispatchID标记接口中的每个公共方法/属性。然后该类必须从该接口继承 - 以下面的方式。

[Guid("BE5E0B60-F855-478E-9BE2-AA9FD945F177")]
[InterfaceType(ComInterfaceType.InterfaceIsIDispatch)]
public interface ICriteria
{
    [DispId(1)]
    int ID { get; set; }
    [DispId(2)]
    string RateCardName { get; set; }
    [DispId(3)]
    string ElectionType { get; set; }
}


[Guid("3023F3F0-204C-411F-86CB-E6730B5F186B")]    
[ClassInterface(ClassInterfaceType.None)]
[ProgId("MyNameSpace.Criteria")]
public class Criteria : ICriteria
{
    public int ID { get; set; }
    public string RateCardName { get; set; }
    public string ElectionType { get; set; }
}

调度 ID 为您提供了在类中移动项目的能力,而且您现在可以向类添加新内容,而不会破坏二进制兼容性。

I found a reliable way to both provide Intellisense for .NET objects in VB6, while at the same time not breaking the interface. The key is to mark each public method/property in the interface with DispatchID. Then the class must inherit from this interface - in the manner below.

[Guid("BE5E0B60-F855-478E-9BE2-AA9FD945F177")]
[InterfaceType(ComInterfaceType.InterfaceIsIDispatch)]
public interface ICriteria
{
    [DispId(1)]
    int ID { get; set; }
    [DispId(2)]
    string RateCardName { get; set; }
    [DispId(3)]
    string ElectionType { get; set; }
}


[Guid("3023F3F0-204C-411F-86CB-E6730B5F186B")]    
[ClassInterface(ClassInterfaceType.None)]
[ProgId("MyNameSpace.Criteria")]
public class Criteria : ICriteria
{
    public int ID { get; set; }
    public string RateCardName { get; set; }
    public string ElectionType { get; set; }
}

What the dispatch ID gives you is the ability to move around items in the class, plus you can now add new things to the class and not break the binary compatibility.

半步萧音过轻尘 2024-09-05 23:00:43

我认为这概括了这一点:

使用双接口的类型允许
客户端绑定到特定的
界面布局。任何变化
未来版本的布局
类型或任何基本类型都会破坏 COM
绑定到接口的客户端。经过
默认情况下,如果
ClassInterfaceAttribute 属性是
未指定,仅调度
使用接口。

http://msdn.microsoft.com/en-us/library/ms182205.aspx

它增加了使用自动双重属性更改该类中的某些内容会在类更改时破坏其他人的代码的可能性。如果让消费者能够做一些很可能在未来给他们带来问题的事情。

下一个选项是 ClassInterfaceType.AutoDual。这也是获得早期绑定支持的快速而肮脏的方法(并使方法显示在 VB6 IntelliSense 中)。但通过更改方法的顺序或添加新的重载也很容易破坏兼容性。避免使用 AutoDual。

http://www.dotnetinterop.com/faq/?q=ClassInterface

我终于找到了有关 AutoDual 的情况及其工作原理的链接:

http://social.msdn.microsoft.com/Forums/en-US/csharpgeneral/thread/7fa723e4-f884-41dd-9405-1f68afc72597

针对 AutoDual 的警告并不是
事实上双接口很糟糕但是
事实上它会自动生成
COM 接口为您服务。那很糟糕。
每次COM接口都必须是
重新生成后你会得到一个新的 GUID 并且
潜在的新成员。如果 GUID
改变然后你会得到一个全新的
就 COM 而言,接口/类
担心的。对于早期绑定你会
每次都必须重建客户端
界面已重新生成。这
首选方法是定义
COM 类接口显式地带有
GUID。然后全部提前绑定
客户端可以使用定义的接口
不用担心它会改变
他们在开发过程中。因此
推荐的选项是“无话可说”
CLR 不会自动生成它
你。您仍然可以实施双重
如果您需要的话,尽管有接口。

I think this sums it up:

Types that use a dual interface allow
clients to bind to a specific
interface layout. Any changes in a
future version to the layout of the
type or any base types will break COM
clients that bind to the interface. By
default, if the
ClassInterfaceAttribute attribute is
not specified, a dispatch-only
interface is used.

http://msdn.microsoft.com/en-us/library/ms182205.aspx

It increases the possibility that changing something in that class with the auto dual attribute will break someone else's code when the class is changed. If gives the consumer the ability to do something that will quite possibly cause them issues in the future.

The next option is ClassInterfaceType.AutoDual. This is the quick and dirty way to get early binding support as well (and make the methods show up in VB6 IntelliSense). But it's also easy to break compatibility, by changing the order of methods or adding new overloads. Avoid using AutoDual.

http://www.dotnetinterop.com/faq/?q=ClassInterface

I finally found the link that talks about what is going on with AutoDual and how it works:

http://social.msdn.microsoft.com/Forums/en-US/csharpgeneral/thread/7fa723e4-f884-41dd-9405-1f68afc72597

The warning against AutoDual isn't the
fact that dual interfaces is bad but
the fact that it auto-generates the
COM interface for you. That is bad.
Each time the COM interface has to be
regenerated you'll get a new GUID and
potentially new members. If the GUID
changes then you get a brand new
interface/class as far as COM is
concerned. For early binding you'd
have to rebuild the clients each time
the interface was regenerated. The
preferred approach is to define the
COM class interface explicitly with a
GUID. Then all the early binding
clients can use the defined interface
and not worry about it changing on
them during development. That is why
the recommended option is None to tell
the CLR not to auto-generate it for
you. You can still implement the dual
interface though if you need it.

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文