2009-04-12 1 views
1

Я очень новичок в C# (только что начал учиться на прошлой неделе).Использование массивов и указателей в C# с C DLL

У меня есть пользовательский DLL, написанный на C с помощью следующей функции:

DLLIMPORT void test_function (double **test) 

То, что я ищу, чтобы сделать, это есть указатель с C# для массива «тест».

Итак, если в функции DLL у меня есть тест [0] = 450.60, test [1] = 512.99 и т. Д. Я хочу иметь это доступное в моей программе на C#.

В C# программы у меня есть что-то подобное:

namespace TestUtil 
{ 
    public class Echo 
    { 
    public double[] results = new double[10]; 
    public double[] results_cpy = new double[10]; 


    [DllImport("test_dll.dll", CallingConvention = CallingConvention.Cdecl)] 
    static extern unsafe void test_function(ref double[] Result); 

    public unsafe void Tell() 
    { 
     results[0] = 0.0; 
     results[1] = 0.0; 

     results_cpy[0] = 0.0; 
     results_cpy[1] = 0.0; 

     test_function(ref results); 
     results_cpy[0] = (double)results[0] + (double)results[1] ; 
    } 
    } 
} 

В функции библиотеки DLL 'test_function' Я использовал следующее:

*test[0] = 450.60; 
*test[1] = 512.99; 

Внутри DLL все нормально (я использовал поле сообщения в DLL, чтобы проверить, какие значения были применены). Назад в результатах программы C# [0] 'кажется прекрасным, и я могу получить значения из него, но «результаты [1]» дают мне ошибку индекса за пределами границ. Я знаю это, потому что, если я опускаю '+ (double) результаты [1]', я не получаю ошибки. Кроме того, если я не пытаюсь в DLL модифицировать 'test [1]', он сохраняет исходное значение из C# (в моем примере 0.0).

Очевидно, что я не делаю что-то правильно, но это самое близкое, что мне удалось добиться от его работы вообще. Все, что я пробовал, терпит неудачу.

Любая помощь была бы принята с благодарностью.

ответ

1

Я предполагаю, что вы уже знаете, C++; если это так, вам действительно стоит посмотреть на C++/CLI, который позволяет вам легко использовать управляемый код (.NET) из C++. Код, который вы показали выше, действительно не очень похож на C# (вы должны полностью избегать unsafe).

+0

+1 для предотвращения небезопасности. Практически всегда есть лучший способ. – Rap

0

Аналогичный вопрос о SO here. Вы смотрите на непрозрачный указатель, так что это, скорее всего, система InPtr по-ref, как описано в другом потоке.

Кстати, почему бы не сделать его двойным * вместо двойного **. Думаю, это облегчило бы жизнь.

5

Нет необходимости в небезопасном коде. На самом деле, нет необходимости проходить по ссылке вообще. Если ваша подпись выглядит следующим образом:

void test_function (double *test) 

и ваш импорт выглядит следующим образом:

static extern void test_function(double[] Result); 

Тогда все должно работать нормально. То есть, предполагая, что вам нужно только модифицировать массив и не возвращать полностью новый массив.

 Смежные вопросы

  • Нет связанных вопросов^_^