2011-02-07 15 views
5

Quiero usar mis funciones C++ nativas de dll en código C# administrado. Pero mis funciones toman argumentos como std :: vector & - una referencia vectorial ... ¿Cómo puedo implementar este argumento en la declaración dllimport? Sé por ejemplo que hay IntPtr y más, pero ¿qué será de std :: vector <>?Usando código C++ nativo en C# - problema con std :: vector

+1

Esto probablemente va a ser muy difícil, si no imposible. ¿Puedes proporcionar una interfaz 'C' para tu biblioteca' C++ 'y usar eso en su lugar? – ereOn

+2

Usa C++/CLI para compilar clases contenedoras. –

+1

Si bien puede utilizar las soluciones sugeridas para lograr algo similar a lo que necesita, si entiendo correctamente, usted controla tanto el código para el dll no administrado como la aplicación administrada.En este caso, tal vez sería mejor proporcionar envoltorios de C++/CLI para sus funciones en el dll y llamarlos directamente desde C#. Tal vez deberías echarle un vistazo a STL.Net también. Aquí hay un enlace a un manual: http://msdn.microsoft.com/en-us/library/ms379600%28v=vs.80%29.aspx – ds27680

Respuesta

5

Exportaría las funciones "C" que envuelven la funcionalidad necesaria y P/Invoquelas desde C#. Tal función "C" podría exponer los datos std::vector<> como un puntero y el tamaño del búfer de datos.

Digamos por ejemplo que usted tiene una std::vector<byte_t> en una clase Buffer:

class Buffer 
{ 
public: 
    const std::vector<byte_t>& GetData() const { return data_; } 

private: 
    std::vector<byte_t> data_; 
}; 

A continuación, puede exportar una función de "C" para adecuadamente el alcance del Buffer que desea utilizar:

Buffer* CreateBuffer(); 

Y probablemente desee hacer algo en el lado nativo que llene el std::vector<byte_t> con datos:

void DoSomethingThatProduceData(Buffer* buffer); 

continuación, puede leer los datos:

void GetBufferData(const Buffer* buffer, const byte_t** data, int* size); 

Y por último, limpiar:

void DestroyBuffer(Buffer* buffer); 

traducir esas declaraciones "C" a P/Invoke queridos en el lado C#:

[DllImport("YourBufferLib.dll")] 
static extern IntPtr CreateBuffer(); 

[DllImport("YourBufferLib.dll")] 
static extern void DoSomethingThatProduceData(IntPtr buffer); 

[DllImport("YourBufferLib.dll")] 
static extern void GetBufferData(IntPtr buffer, out IntPtr data, out Int32 size); 

[DllImport("YourBufferLib.dll")] 
static extern void DestroyBuffer(IntPtr buffer); 

Sería una buena cosa para envolver esas llamadas en el lado administrado en una clase IDisposable que asegure que el recurso nativo es correctamente cl eaned arriba.

[El, algo trivial, detalles de implementación de las funciones de "C" son obviamente deja como ejercicio para el lector.]

0

vectores STL son métodos con plantilla no administrados. En teoría, puede calcular los desplazamientos a los métodos correspondientes del vector para generar código y llamarlo. No puede usar DllImport porque los vectores STL son solo una biblioteca de plantillas que no son métodos exportados. Se podría, por supuesto, escribir un envoltorio estilo de C para llamar a métodos específicos como

int GetSize(vector<xxx> *vec) 
{ 
    return vec.size(); 
} 

Pero no quiero hacer eso porque las muchas transiciones unmanged administrados necesarios para que esto traerá su aplicación a un alto repentino. Si necesita manipular stl vectores su mejor opción es utilizar C++ administrado y llamar desde C# a su dll administrado C++ para manipular los vectores como desee. En muchas compañías, el uso de Managed C++ fue prohibido debido a que las personas no prestaban atención al costo de las transiciones administradas no administradas, lo que causó que C++ perdiera su principal activo: Speed.

Suyo, Alois Kraus