本文介绍了如何将LPTSTR(C ++)变量转换为C#字符串。的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧! 问题描述 29岁程序员,3月因学历无情被辞! 大家好, 我对这个转换问题有疑问。 从C#组件我需要调用C ++ Dll方法: C ++ extern C { __declspec(dllexport) bool getVal(LPTSTR& ab); } 在c#中我定义一个字符串'cd。 C# [DllImport( .. .dll)] public static extern bool getVal(???); private void Testbutton_Click( object sender,EventArgs e) { string cd ???? getVal(?? cd ???)); 问题: 如何从C#调用方法,以便将C ++ LPTSTR变量中定义的字符串复制到C#字符串变量中? 我不知道返回的字符串有多大。 **更新** 这是C ++方法: C ++ extern C { __declspec( dllexport) bool getVal(LPTSTR& retVal); } 这就是retVal的设定方式: extern bool getVal(LPTSTR& retVal) { 。 。 。 String ^ val = sr-> ReadLine(); retVal =(LPTSTR)(Marshal :: StringToHGlobalAnsi(val))。ToPointer(); 。 。 。 return true ; } 我需要帮助从C#调用此方法。 目前我有: C# [DllImport( myLibrary.dll,CallingConvention = CallingConvention.Cdecl)] public static extern bool getVal([MarshalAsAttribute(UnmanagedType) .LPTStr)] out String retVal); private void Testbutton_Click(对象发​​件人,EventArgs e) { string myVal; getVal( out myVal)); 我在myVal中得到的是垃圾,就像中文字符(ANSI / Unicode问题??),而不是我可以打印出来的值,如果调试dll,我访问val C ++变量。 也许从String ^到LPTSTR的转换不正确?解决方案 默认情况下,C string是 marshaled 作为P / Invoke中的.NET字符串。确定,您可以使用属性 System.Runtime.InteropServices.MarshalAsAttribute : https://msdn.microsoft.com/en-us/library/system.runtime.interopservices。 marshalasattribute%28v = vs.110%29.aspx [ ^ ]。 该属性应该应用于单独的方法参数,作为目标 AttributeTargets.Parameter 支持(请参阅上面的属性声明)。 说,对于 LPTSRT ,您需要使用 https://msdn.microsoft.com/en-us/library/6e0wtfh2%28v=vs.110%29.aspx [ ^ ]; System.Runtime.InteropServices.UnmanagedType.LPTStr : https://msdn.microsoft.com/en-us/library/system.runtime.interopservices.unmanagedtype%28v=vs.110%29.aspx [ ^ ]。 顺便说一下,你不必使用 externC只是为了有更多的功能名称。为什么不直接使用默认的装饰(损坏)名称(参见 https://en.wikipedia.org/wiki/Name_mangling [ ^ ])?您可以使用一些二进制转储实用程序找到确切的装饰名称,例如dumpbin.exe( https:/ /msdn.microsoft.com/en-us/library/c1h23y6c.aspx [ ^ ],可以在Visual Studio命令提示符下执行,并直接在 EntryPoint中使用 命名参数(属性) System.Runtime.InteropServices.DllImportAttribute : https://msdn.microsoft.com/en-us/library/Aa984739%28v=VS.71%29.aspx [ ^ ], https://msdn.microsoft.com/en-us/library/system.runt ime.interopservices.dllimportattribute%28v = vs.110%29.aspx [ ^ ], https://msdn.microsoft.com/en-us/library/system.runtime.interopservices.dllimportattribute .entrypoint(v = vs.110).aspx [ ^ ]。 -SA Hi everyone,I have an issue with this conversion problem.From a C# component I need to call a C++ Dll method:C++extern "C" { __declspec(dllexport) bool getVal(LPTSTR& ab); }In c# I define a string 'cd.C#[DllImport("...dll")]public static extern bool getVal(???);private void Testbutton_Click(object sender, EventArgs e){ string cd???? getVal(??cd???));Question:How do I call, from C#, the method so that the string defined in the C++ LPTSTR variable is copied into the C# string variable?I don't know how big the returned string can be.** UPDATE**This is the C++ method: C++extern "C"{ __declspec(dllexport) bool getVal(LPTSTR& retVal);}this is how retVal is set:extern bool getVal(LPTSTR& retVal) {... String^ val = sr->ReadLine(); retVal = (LPTSTR)(Marshal::StringToHGlobalAnsi(val)).ToPointer();... return true; }I need help calling this method from C#.Currently I have: C#[DllImport("myLibrary.dll", CallingConvention = CallingConvention.Cdecl)]public static extern bool getVal([MarshalAsAttribute(UnmanagedType.LPTStr)] out String retVal);private void Testbutton_Click(object sender, EventArgs e){ string myVal; getVal(out myVal));what I get in myVal is garbage, like chinese chars (ANSI/Unicode issue??), not the value I can print out and read if, debugging the dll, I access the val C++ variable.Maybe the conversion from String^ to LPTSTR is not correct? 解决方案 By default, C string is marshaled as .NET string in P/Invoke. To be certain, you can use the attribute System.Runtime.InteropServices.MarshalAsAttribute:https://msdn.microsoft.com/en-us/library/system.runtime.interopservices.marshalasattribute%28v=vs.110%29.aspx[^].The attribute should be applied to separate method parameter, as the target AttributeTargets.Parameter is supported (please see the attribute declaration above).Say, for LPTSRT, you need to use https://msdn.microsoft.com/en-us/library/6e0wtfh2%28v=vs.110%29.aspx[^];System.Runtime.InteropServices.UnmanagedType.LPTStr:https://msdn.microsoft.com/en-us/library/system.runtime.interopservices.unmanagedtype%28v=vs.110%29.aspx[^].By the way, you don't have to use extern "C" just to have undercorated function name. Why not using default decorated (mangled) names directly (see https://en.wikipedia.org/wiki/Name_mangling[^])? You can find out exact decorated name using some binary dump utility, such as "dumpbin.exe" (https://msdn.microsoft.com/en-us/library/c1h23y6c.aspx[^], can be executed under the "Visual Studio Command Prompt") and use it directly in the EntryPoint named parameter (property) of System.Runtime.InteropServices.DllImportAttribute:https://msdn.microsoft.com/en-us/library/Aa984739%28v=VS.71%29.aspx[^],https://msdn.microsoft.com/en-us/library/system.runtime.interopservices.dllimportattribute%28v=vs.110%29.aspx[^],https://msdn.microsoft.com/en-us/library/system.runtime.interopservices.dllimportattribute.entrypoint(v=vs.110).aspx[^].—SA 这篇关于如何将LPTSTR(C ++)变量转换为C#字符串。的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持! 上岸,阿里云!
07-25 13:06