Для того, чтобы скрыть реализацию функции, я обычно пишу следующий C++ код и разоблачить свою функцию как «интерфейсы»Как использовать C++-интерфейс в C#?
// the interface to expose
class ICalcService
{
public:
virtual double Multiple(double a, double b) const = 0;
};
// the implementation of the interface
class CalcService final : public ICalcService
{
virtual double Multiple(double a, double b) const override
{
return a * b;
}
};
// expose the 'CreateCalcService' to mydll.dll as C function
extern "C" __declspec(dllexport) void CreateCalcService(void** obj)
{
*obj = new CalcService();
}
И типичное использование в C++ является
// typical way to consume the interface in C++
void test_cpp_code()
{
ICalcService* calc;
CreateCalcService(reinterpret_cast<void**>(&calc));
cout << calc->Multiple(15, 23) << endl;
}
сейчас Я хотел бы использовать его в коде C#. После периода исследований, я написал следующий код
using System.Runtime.InteropServices;
class Program
{
interface ICalcService
{
double Multiple(double a, double b);
}
[DllImport("mydll.dll", CallingConvention = CallingConvention.Cdecl)]
private extern static void CreateCalcService(out object obj);
static void Main(string[] args)
{
object o;
CreateCalcService(out o);
var calc = o as ICalcService;
calc.Multiple(14, 29);
}
}
Но это не будет работать, как я ожидал. Вместо этого исключение было выбрано в строке CreateCalcService(out o)
.
Помощник по удаленной работе «InvalidVariant» обнаружил проблему в «xx \ xx \ myloader.vshost.exe». Дополнительная информация: Недействительный VARIANT был обнаружен во время преобразования из неуправляемого VARIANT в управляемый объект. Передача недействительных VARIANT в среду CLR может вызвать неожиданные исключения, повреждение или потерю данных. Если для этого исключения есть обработчик, программа может быть безопасно продолжена. Необработанное исключение типа «System.Runtime.InteropServices.InvalidOleVariantTypeException» произошло в myloader.exe Дополнительная информация: Указанный вариант OLE недопустим.
Может ли кто-нибудь любезно сообщить мне, в чем проблема и как заставить его работать? например неправильная подпись C# dllimport.
Заранее благодарен!
Быстро разочарован тем, что нет встроенного подхода. Первая альтернатива на самом деле не изящна, в то время как вторая не пересекается с платформой :(В любом случае, спасибо за информацию! –