Visual Basic .Net 中等效的公共虚拟外部字符串

Posted

技术标签:

【中文标题】Visual Basic .Net 中等效的公共虚拟外部字符串【英文标题】:public virtual external string equivalent in Visual Basic .Net 【发布时间】:2017-07-18 14:58:06 【问题描述】:

我正在翻译一个用 C# 编写的 dll,但在翻译字符串声明时遇到了一些麻烦。 C#中的代码如下:

using BGMC_TypeDefs;
using stdole;
using System.Runtime.CopilerServices;
using System.Runtime.InteropServices;

namespace bgmcproject

  [Guid("3C69B26B-8D17-11D3-BA9C-00E09803AA6A")]
  [ClassInterface(0)]
  [ComSourceInterfaces("bgmcproject.__bgmc\0\0")]
  [TypeLibType(32)]
  [ComImport]
  public class bgmcClass : _bgmc, bgmc, __bgmc_Event
  
    [DispId(1745027134)]
    public virtual extern string szMachineImg  [DispId(1745027134), MethodImpl(MethodImplOptions.InternalCall, MethodCodeType = MethodCodeType.Runtime)] [param: MarshalAs(UnmanagedType.BStr), In] set; 
  

我已经翻译了一些代码,我最终得到了这个:

Imports BGMC_TypeDefs
Imports stdole
Imports System.Runtime.CompilerServices
Imports System.Runtime.InteropServices

Namespace bgmcproject
   <Guid("3C69B26B-8D17-11D3-BA9C-00E09803AA6A")>
   <ClassInterface(0)>
   <ComSourceInterfaces("bgmcproject.__bgmc\0\0")>
   <TypeLibType(32)>
   <ComImport>
   Public Class bgmcClass
      Implements _bgmc, bgmc, __bgmc_Event

      <DispId(1745027134)>
      Public virtual external String szMachineImg _ 
      (<DispId(1745027134), MethodImpl(MethodImplOptions.InternalCall, _
               MethodCodeType = MethodCodeType.Runtime)> _
               <param MarshalAs(UnmanagedType.BStr), In> Set )
   End Class
End Namespace

我想知道szMacingeImg的声明怎么写。 另外,如果您能帮我澄清一下,“实现”语句是否正确,或者我应该写“继承”。非常感谢。

【问题讨论】:

Implements 适用于接口,Inherits 适用于类。 非常感谢!知道如何翻译“公共虚拟外部”部分吗? public 直接映射。 virtual 我想应该是 Overridable。我不确定extern,不过……这不是我在 VB 中需要做的事情。 再次感谢!你认为我可以把它写成一个函数吗?像这样: 。公共可重写函数 szMachineImg( Set) As String End Function 不幸的是,你现在已经超出了我的专业范围。对不起。 :( 【参考方案1】:

这是 extern 关键字的罕见用法,没有随附的 DllImport 属性。 extern 关键字与带有 MethodImplOptions.InternalCall 枚举值的 MethodImpl 属性相结合,表示代码是在 CLR 本身中实现的: How does extern work in C#?(见 Dan Abramov 的回答)。

在 VB 中,我认为您不能单独在“set”或“get”上指定属性,除非该属性以“长格式”编写,因此与您的代码等效的 VB 应该是:

Imports Microsoft.VisualBasic
Imports System.Runtime.CopilerServices
Imports System.Runtime.InteropServices

Namespace bgmcproject
  <Guid("3C69B26B-8D17-11D3-BA9C-00E09803AA6A"), ClassInterface(0), ComSourceInterfaces("bgmcproject.__bgmc" & vbNullChar & vbNullChar), TypeLibType(32), ComImport>
  Public Class bgmcClass
      Inherits _bgmc
      Implements bgmc, __bgmc_Event

    <DispId(1745027134)>
    Public Overridable WriteOnly Property szMachineImg() As String
        <DispId(1745027134), MethodImpl(MethodImplOptions.InternalCall, MethodCodeType := MethodCodeType.Runtime), param:= MarshalAs(UnmanagedType.BStr), [In]>
        Set(ByVal value As String)
        End Set
    End Property
  End Class
End Namespace

另外,关于第一个 _bgmc 类型是类还是接口,我假设它是一个类,但您需要检查一下。

【讨论】:

非常感谢您的帮助,一切都很好,除了“param:”部分。我试着把它写成:param:=MarshalAs(UnmanagedType.BStr) 但它告诉我“param”没有定义,如果我只输入“param:”。我需要导入库吗? @LuisEnriquez:我已将答案更新为使用“param := ...”。 再次感谢,我已经把它写成“param:=”,但它仍然告诉我“类型'参数未定义”。我正在使用 Visual Studio 2017,在潜在的修复中它告诉我使用“[ParamArray]”或“DefaultParameterValue”。如果我使用DefaultParameterValue,它会告诉我需要更改 MarshalAs,因为它可能由于其保护级别而无法访问。所以如果我把它写成DefaultParameterValue(MarshalAsAttribute(UnmanagedType.BStr))DefaultParameterValue 被标记为可以使用,但现在我在MarshalAsAttribute 上得到一个错误。也许我缺少一些参数参考?

以上是关于Visual Basic .Net 中等效的公共虚拟外部字符串的主要内容,如果未能解决你的问题,请参考以下文章

在 Visual Basic .NET 中提取 Zip 文件

Visual Basic .NET 中消息框中的按钮

如何在 Visual Basic .NET 中找到默认音频设备?

在 asp.net 中插入后获取主键(visual basic)

在 asp.net(访问数据库)中编写更新查询(visual basic)

我的 ASP.NET / Visual Basic 代码有啥问题?