2012-06-18 6 views
15

私はC++で LPCWSTRを表しIntPtr値であるStringHandleフィールドを持つクラスを使用しています。文字列値にC#の.NETポイントでのIntPtrを作る

internal IntPtr StringHandle; // LPCWSTR 

は、私は文字列を持っていることを今言う:それはC++ LPCWSTRのようなものであるように、string x = "abcdefg"

は、どのように私は文字列の先頭を指すように文字列のハンドルを使用することができますか?

+0

なぜそれをしたいですか? –

+0

ネイティブコード(C++)のみに存在するインターフェイスで作業しているため、.NETからInteropsを使用しています。しかし、StringHandleを持つクラスは私のものではなく、私は変更したくありません。 –

+6

これは彼が働いているライブラリが期待しているものなので。すべてに.NETラッパーが組み込まれているわけではなく、フレームワーク内でさえ、低レベルのWindowsメッセージのようなものを扱う際には、Marshalクラスを使用することができます。 – KeithS

答えて

24

にStringTo *メソッドのいずれかを使用します。あなたはそのように行うことができます。

IntPtr strPtr = Marshal.StringToHGlobalUni(x); 

も、あなたは、アンマネージメモリを解放することを確認する必要があります。

Marshal.FreeHGlobal(strPtr); 

それは、try /ついにこのすべてを行うことをお勧めします。

+0

私はCOMを使っているので、実際にこのMarshal.StringToCoTaskMemUniが必要でしたが、ありがとうございました –

1

あなたは、あなたが最初のアンマネージメモリに文字列をコピーし、その場所からIntPtrを取得する必要がありMarshalクラス

7

管理文字列ガベージコレクタがヒープを圧縮するときに、メモリ内でを移動します。したがって、彼らは安定したアドレスを持たず、直接LPCWSTRにキャストできません。 GCHandle.AddrOfPinnedObjectを使用するには、文字列をGCHandle.Alloc()で固定するか、Marshal.StringToHGlobalUni()を使用してアンマネージメモリにコピーする必要があります。

アドレスがしばらく安定している必要がある場合は、コピーを強くお勧めします。

+0

文字列の 'AddrOfPinnedObject'は文字データ(' LPCWSTR')のポインタを質問に記載していますか? (http://www.drdobbs.com/pinning-in-managed-c/184403869による:はい) –

関連する問題