是否可以在 C# 和非托管 C++ 之间共享枚举声明?
声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow
原文地址: http://stackoverflow.com/questions/954321/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me):
StackOverFlow
Is it possible to share an enum declaration between C# and unmanaged C++?
提问by sean e
Is there a way to share an enum definition between native (unmanaged) C++ and (managed) C#?
有没有办法在本机(非托管)C++ 和(托管)C# 之间共享枚举定义?
I have the following enum used in completely unmanaged code:
我在完全非托管的代码中使用了以下枚举:
enum MyEnum { myVal1, myVal2 };
Our application sometimes uses a managed component. That C# component gets the enum item values as ints via a managed C++ interop dll (from the native dll). (The interop dll only loads if the C# component is needed.) The C# component has duplicated the enum definition:
我们的应用程序有时会使用托管组件。该 C# 组件通过托管的 C++ 互操作 dll(来自本机 dll)获取作为整数的枚举项值。(互操作 dll 仅在需要 C# 组件时才加载。)C# 组件复制了枚举定义:
public enum MyEnum { myVal1, myVal2 };
Is there a way to eliminate the duplication without turning the native C++ dll into a managed dll?
有没有办法在不将本机 C++ dll 转换为托管 dll 的情况下消除重复?
采纳答案by jjxtra
You can use a single .cs file and share it between both projects. #include
in C++ on a .cs file should be no problem.
您可以使用单个 .cs 文件并在两个项目之间共享它。#include
在 C++ 上一个 .cs 文件应该没问题。
This would be an example .cs file:
这将是一个示例 .cs 文件:
#if !__LINE__
namespace MyNamespace
{
public
#endif
// shared enum for both C, C++ and C#
enum MyEnum { myVal1, myVal2 };
#if !__LINE__
}
#endif
If you want multiple enums in one file, you can do this (although you have to temporarily define public to be nothing for C / C++):
如果你想在一个文件中包含多个枚举,你可以这样做(尽管你必须临时定义 public 为 C/C++ 的空):
#if __LINE__
#define public
#else
namespace MyNamespace
{
#endif
public enum MyEnum { MyEnumValue1, MyEnumValue2 };
public enum MyEnum2 { MyEnum2Value1, MyEnum2Value2 };
public enum MyEnum3 { MyEnum3Value1, MyEnum3Value2 };
#if __LINE__
#undef public
#else
}
#endif
回答by Steffen
Unmanaged C++ and C# live in two different worlds, so no there is no way to use the same enum, without changing the c++ DLL into a managed one.
非托管 C++ 和 C# 存在于两个不同的世界中,因此如果不将 C++ DLL 更改为托管的,就无法使用相同的枚举。
And even then, you'd probably need the duplication in the managed C++ DLL.
即便如此,您也可能需要在托管 C++ DLL 中进行复制。
A C++ enum is much like a list of constants, whereas a C# enum inherits the Enum class, and thus provides quite a few "tricks". So as you can see, they're verydifferent.
C++ 枚举很像一个常量列表,而 C# 枚举继承了 Enum 类,因此提供了很多“技巧”。正如你所看到的,它们是非常不同的。
If it doesn't matter whether the native C++ DLL is native or managed, I'd turn it into a managed one and wrap the native calls inside a managed C++ Layer.
如果本机 C++ DLL 是本机还是托管无关紧要,我会将其转换为托管并将本机调用包装在托管 C++ 层中。
That way you can have the enum duplication inside the C++ DLL, and also you can get rid of all the interop at the same time :-)
这样你就可以在 C++ DLL 中有枚举重复,而且你可以同时摆脱所有的互操作 :-)
回答by sharptooth
You can expose the C# library to COM and then import the type library into the unmanaged code - this way you will be able to use the enum defined in C# library in the unmanaged library.
您可以将 C# 库公开给 COM,然后将类型库导入非托管代码 - 这样您就可以在非托管库中使用 C# 库中定义的枚举。
回答by Adrian Conlon
I've had the same problem in the past and solved it using preprocessor definitions.
我过去遇到过同样的问题,并使用预处理器定义解决了它。
In your unmanaged code, inside a header that can also be included by your managed wrapper, place your enumeration items into a #define.
在您的非托管代码中,在您的托管包装器也可以包含的标头内,将您的枚举项放入 #define 中。
Then, in your managed and unmanaged enumeration definitions, use the same #define for both usages.
然后,在您的托管和非托管枚举定义中,对这两种用法使用相同的 #define。
The movement of the enumerations between the managed and unmanaged world looks slightly nasty (basically a cast is needed), but to your caller in the unmanaged world, it'll look and feel fine.
托管和非托管世界之间的枚举移动看起来有点令人讨厌(基本上需要强制转换),但对于非托管世界中的调用者来说,它看起来和感觉都很好。
Good luck,
祝你好运,
回答by Johan Torp
Thanks for sharing!
感谢分享!
I played around a bit and found a way to have multiple enum and constant declarations without having tons of extra lines :)
我玩了一会儿,找到了一种方法来拥有多个枚举和常量声明而没有大量额外的行:)
// This is a valid C, C++ and C# file :)
#if __LINE__
#define public
#else
namespace MyCSharpNamespace{
#endif
public enum MyConstant { MaxStr = 256 };
public enum MyEnum1{ MyEnum1_A, MyEnum1_B };
public enum MyEnum2{ MyEnum2_A, MyEnum2_B };
#if __LINE__
#undef public
#else
}
#endif
Remember to name your file *.cs
请记住将您的文件命名为 *.cs