C# 以更人性化的方式编组字符**

C# 以更人性化的方式编组字符**,c#,c++,string,marshalling,C#,C++,String,Marshalling,我在C#中有以下接口方法声明: pOutputformat实际上是C中的字符**++ 我需要执行Marshal.PtrToStringAnsi(pOutputformat)以获取实际字符串 是否有一些编组属性可以直接将pOutputformat转换为out字符串,而不是使用IntPtr 这是C++方法所做的: HRESULT CLAVAudio::GetOutputDetails(const char **pOutputFormat, int *pnChannels, int *pSampleR

我在C#中有以下接口方法声明:

pOutputformat实际上是C中的字符**++

我需要执行
Marshal.PtrToStringAnsi(pOutputformat)
以获取实际字符串

是否有一些编组属性可以直接将pOutputformat转换为out字符串,而不是使用IntPtr

<>这是C++方法所做的:

HRESULT CLAVAudio::GetOutputDetails(const char **pOutputFormat, int *pnChannels, int *pSampleRate, DWORD *pChannelMask)
{
  if(!m_pOutput || m_pOutput->IsConnected() == FALSE) {
    return E_UNEXPECTED;
  }
  if (m_avBSContext) {
    if (pOutputFormat) {
      *pOutputFormat = get_sample_format_desc(SampleFormat_Bitstream);
    }
    return S_FALSE;
  }
  if (pOutputFormat) {
    *pOutputFormat = get_sample_format_desc(m_OutputQueue.sfFormat);
  }
  if (pnChannels) {
    *pnChannels = m_OutputQueue.wChannels;
  }
  if (pSampleRate) {
    *pSampleRate = m_OutputQueue.dwSamplesPerSec;
  }
  if (pChannelMask) {
    *pChannelMask = m_OutputQueue.dwChannelMask;
  }
  return S_OK;
}
这是你能做的最好的。这是不可避免的。如果尝试以
out string OutputFormat
的形式封送,封送器将对本机代码返回的指针调用
CoTaskMemFree
。这一切都以眼泪结束

问题仍然是谁负责解除分配
pOutputformat
指向的内存?只有你知道答案


有人想知道为什么这个COM接口的设计者选择使用C字符串而不是COM
BSTR

,这取决于该方法使用参数a
out-StringBuilder
的方式。out-StringBuilder会使应用程序崩溃,而StringBuilder只会返回一个填充了指针而不是值的StringBuilder(4字节的垃圾)是的,这可能发生。编组输出参数有点恼人,因为它取决于方法处理它以及分配内存还是调用函数。好的,C++中的方法就像你所期望的那样,把指针放到内部字符串到pOutPt格式,然后我用PtrToStringAnsi读它。有一种方法可以以某种方式将参数声明为out string,因为它显然不适用于“out string”你不能调用C++实例方法。它在访问MyDead和MyavbsValx成员时不会崩溃。这是不可能的。这是不好的。我知道它完全缺少BSTR,但是我不能做很多事情:(不管从C++代码来看,我似乎有责任释放任何东西。“*pOutputFormat=get\u sample\u format\u desc()"放入我的指针。对吗?@MarinoŠimić只有知道它是从哪个堆分配的,或者库为您提供了deallocator,才能释放它。有时库返回静态分配字符串的指针,在这种情况下不需要释放。我们任何人都无法知道这些细节。我找到了get_sample_表单at_desc:const char*get_sample_format_desc(LAVAudioSampleFormat sfFormat){return sample_format_strings[sfFormat];}似乎不需要解除分配,因为它只从静态const char*sample_format_strings[]返回字符串={“16位整数”、“24位整数”、“32位整数”、“8位整数”、“32位浮点”、“位流”}“你很好。”代码>马歇尔。PtotoStRangangsI/C>是你的基本条件。我接受你的回答,感谢今天的教学课。学习东西总是很好,尤其是因为我不太擅长C++和这种互操作。
HRESULT CLAVAudio::GetOutputDetails(const char **pOutputFormat, int *pnChannels, int *pSampleRate, DWORD *pChannelMask)
{
  if(!m_pOutput || m_pOutput->IsConnected() == FALSE) {
    return E_UNEXPECTED;
  }
  if (m_avBSContext) {
    if (pOutputFormat) {
      *pOutputFormat = get_sample_format_desc(SampleFormat_Bitstream);
    }
    return S_FALSE;
  }
  if (pOutputFormat) {
    *pOutputFormat = get_sample_format_desc(m_OutputQueue.sfFormat);
  }
  if (pnChannels) {
    *pnChannels = m_OutputQueue.wChannels;
  }
  if (pSampleRate) {
    *pSampleRate = m_OutputQueue.dwSamplesPerSec;
  }
  if (pChannelMask) {
    *pChannelMask = m_OutputQueue.dwChannelMask;
  }
  return S_OK;
}
Marshal.PtrToStringAnsi(pOutputformat)