(原創) C++ string大亂鬥:C-Style string、STL string與.NET string互轉 (.NET) (C/C++) (C++/CLI) (STL)...

Abstract
由於C++/CLI的加入,現在Visual C++ 9最少就有三種字串:C-Style string、STL string與.NET string,要怎麼在這三種字串互轉呢?

Introduction
使用環境:Visual C++ 9.0 / Visual Studio 2008

網友momo拿到一個硬體讀卡機廠商所提供用C++寫的API,他要在.NET的C#使用,當然這有好幾種解法,因為C++/CLI是唯一可以看懂.NET型別與C/C++型別的語言,最後我建議他用C++/CLI讀進C++寫的API,再包成.NET component給C#用,這樣就面臨了一個問題,如何在C++/CLI將C-Style string(char *s, char s[])轉成.NET的System::String?

Scenario 1:
C-Style string、STL string轉.NET string

這種情況比較多,通常出現在要將C++寫的DLL包成.NET的DLL給C#用。

cstring2netstring.cpp / C++/CLI

1  /*  
2  (C) OOMusou 2007 http://oomusou.cnblogs.com
3 
4  Filename    : cstring2netstring.cpp
5  Compiler    : Visual C++ 9.0 / C++/CLI 2.0
6  Description : Demo how to use string in C++/CLI 2.0
7  Release     : 07/23/2008 1.0
8  */
9 
10  #include " stdafx.h "
11  #include < string >
12 
13  using   namespace System;
14  using   namespace std;
15 
16  int main(array < String ^>   ^ args) {
17    // C string & STL string to .NET string
18    char    c_s[] =   " Hello C " ;
19    string stl_s =   " Hello STL " ;
20   
21    String ^ net_s1 = gcnew String(c_s);
22    String ^ net_s2 = gcnew String(stl_s.c_str());
23   
24    Console::WriteLine(net_s1);
25    Console::WriteLine(net_s2);
26  }
27 


執行結果

Hello C
Hello STL


利用gcnew()就可以將C-Style string與STL string轉成.NET string,雖然看起來很簡單,但當時也是花了一些時間研究才發現。

Scenario 2:
.NETstring轉C-Style string、STL string

我目前是還沒遇到這種需求,只是順便研究一下。

netstring2cstring.cpp / C++/CLI

1  /*  
2  (C) OOMusou 2007 http://oomusou.cnblogs.com
3 
4  Filename    : netstring2cstring.cpp
5  Compiler    : Visual C++ 9.0 / C++/CLI 2.0
6  Description : Demo how to use string in C++/CLI 2.0
7  Release     : 07/23/2008 1.0
8  */
9 
10  #include " stdafx.h "
11  #include < string >
12  #include " stdio.h "
13  #include < iostream >
14  #include < msclr / marshal.h >         // .NET string to C-style string
15  #include < msclr / marshal_cppstd.h >   // .NET string to STL string
16 
17 
18  using   namespace System;
19  using   namespace std;
20  using   namespace msclr::interop;
21 
22  int main(array < String ^>   ^ args) {
23    // .NET String to C string
24    String ^ net_s =   " Hello .NET " ;
25    marshal_context ^ context = gcnew marshal_context();
26    const   char * c_s = context -> marshal_as < const   char *> (net_s);
27    printf( " %s\n " , c_s);
28 
29    // .NET string to STL string 
30    string stl_s = context -> marshal_as < std:: string > (net_s);
31    cout << stl_s << endl;
32    delete context;
33  }


執行結果

Hello .NET
Hello .NET


這個程式要順利執行,主要是靠marshal_as<T>,必須先加上以下3行。這是VC9特有的用法,在VC8之前不能使用。

#include < msclr / marshal.h >         // .NET string to C-style string
#include < msclr / marshal_cppstd.h >   // .NET string to STL string

using   namespace msclr::interop;


25行

marshal_context ^ context = gcnew marshal_context();
const   char * c_s = context -> marshal_as < const   char *> (net_s);


就能利用marshal_as<T>將.NET string轉C-Style string了。

30行

// .NET string to STL string 
string stl_s = context -> marshal_as < std:: string > (net_s);


若要轉成STL string,marshal_as<T>一樣沒問題,只要改成std::string即可。

所有marshal_as<T>能互轉的字串型別,如下整理,夠恐怖了吧。

cppcli_marshal

Conclusion
C++/CLI是個超強語言,同時橫跨.NET與C/C++,也因為如此,所以也比其他語言複雜,其實我非常佩服寫C++/CLI compiler的那些大牛,可以讓兩個完全不同世界的code一起編譯,每次看到將.NET、C、C++與STL的寫法混在一起,竟然還能跑出執行結果,就覺得非常不可思議。

Reference
How to convert from System::String* to Char* in Visual C++
Zuse Cheng Code BlogSTL/CLR: 2008 C++/CLI的利器

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值