Страница: 1 | 2 | 3 | 
		
		 
			   
			 
			 Как передать массив в DLL? В DLL есть такие ф-ция и процедура: ' поиск в массиве значения LVal, возвращает номер элемента SUB SortArrDescend (Arr() AS LONG ) EXPORT Из VB создаю массив() as Long, заполняю его Arr(i)= Clng(RND*1000) и затем вызываю ф-цию ScanArrEqu  
			 
			 Ну так и передай ему ссылку на массив. VB: ArrPtr=VarPtr(Array)   Почему невозможна? Самый, имхо, лучший вариант: ты передаешь указатель на array(0) и длину массива в байтах, DLL создает массив такого размера и копирует в него эти байты, а потом работает как со своим. Потом возвращает либо то, что тебе нужно, либо указатель на arrayDLL(0), после чего ты можешь этот массив либо использовать, либо скопировать обратно к себе в array(0). Да я там уже был. Но это ничего не даёт, т.к. передавая в процедуру указатель на первый элемент и длину массива, не удаётся  из этих данных восстановить массив внутри DLL, чтобы его отсортировать. Делал такую процедуру: А вот по поводу, чтобы длл возвращала указатель на сортированый массив - это зачем, он что переезжает куда то что ли при сортировке? Адрес в памяти ведь прежний остается, после вызова процедуры я снова освежаю листбокс и вижу в нем старый порядок массива. ByVal сразу приводит к падению IDE, неважно указатель ByVal  или размер ByVal.  А собирать с помощью PEEK - POKE тоже ничего не даст, в VB не соберёшь обратно... Видно передать массив функции невозможно. CyRax, ты прирожденный хакер! For FillArr1 = 1 To 10: Arr1(FillArr1) = Arr1(FillArr1 - 1) + 100:  Next FillArr1 Я на такой код любовался минуты три. Теперь я понимаю ужас Ромы, когда я сказал ему, что программы комментировать не надо, они и так понятны. Другими словами: if(a&&!b||c){d*=&(++e==*f++)+g++} А все таки, чувствую, статью "Вызов WinAPI на Visual Basic" написать надо. Буду очень благодарен всем, кто предоставит мне информацию относительно передачи аргументов и указателей в PB, думаю, не помешает, судя по его популярности. А если так? For FillArr1 = 0 To 1000 Step 100: Arr1(FillArr1 / 100) = FillArr1: Next FillArr1 Где-то я уже упоминал, что Обломов рядом со мной - гибрид пчелы и муравья  > For FillArr1 = 0 To 1000 Step 100: Arr1(FillArr1 / 100) = FillArr1: Next FillArr1 Не есть хорошо. Надо: For FillArr1 = 0 To 1000 Step 100: Arr1(FillArr1 \ 100) = FillArr1: Next FillArr1 :D 2brevno: мысль-то хорошая, только, имхо, PB не стоит такого напряга... Ладно бы мы нашли идеальный язык программирования, на котором будем писать до самой смерти, а тут... 16-битный платный компилятор, до сих пор воняющий нафталином QBasic'а... Хотя сделать это стоит хотя бы по той причине, что мы будем иметь шанс продать производителю PB его локализацию  Чувствую без меня эта тема увянет                          Уаааау,    
			
 
  
		
     
  
    
Вопрос: Как передать массив
     
    
Добавлено: 23.01.04 18:55
     
      
  
				
			  
					 
			
				 
    
		
       
    
Автор вопроса:  
     cresta
 cresta
      
       
  
 
    
FUNCTION ScanArrEqu (Arr() AS LONG, LVal AS LONG ) EXPORT AS LONG
    LOCAL hResult AS LONG
    ARRAY SCAN Arr&(), = LVal, TO hResult
    FUNCTION = hResult
END FUNCTION
    ARRAY SORT Arr&(), DESCEND ' сортировка по убыванию
END SUB  
retval& = SCANARREQU ( Arr(), 55) ' возвращает ноль, элемент не найден, хотя 55 заведомо в нем есть
И процедура SORTARRDESCEND Arr() тоже не срабатывает, массив остается не сортирован.
Причём и ф-ция, и процедура из среды РВ работают, тут ошибки нет.
Может, я как-то не так передаю массив в ф-цию?. Через ByVal не получается, VB ругается, что массив надо передавать по ссылке. Или может передача массива в DLL в принципе невозможна? 
				
		
		
					 
			
				 
  
		
     
  
    
Ответы
     
    
Всего ответов: 32
     
      
  
		
	  
			 
	
		 
    
       
    
Номер ответа: 1 
      
Автор ответа: CyRax
 CyRax 




Разработчик Offline Client
ICQ: 204447456 
Вопросов: 180
Ответов: 4229
      
 Web-сайт:  
 Профиль |  | #1
      
Добавлено:  23.01.04 19:17
       
    
       
  
 
    
		
	  
			 
	
		 
    
       
    
Номер ответа: 2 
      
Автор ответа: Sharp
 Sharp










Лидер форума
ICQ: 216865379 
Вопросов: 106
Ответов: 9979
      
 Web-сайт:  
 Профиль |  | #2
      
Добавлено:  23.01.04 20:09
       
    
       
  
 
    
		
	  
			 
	
		 
    
       
    
Номер ответа: 3 
      
Автор ответа: cresta
 cresta


Вопросов: 117
Ответов: 1538
      
 Профиль |  | #3
       
Добавлено:  23.01.04 22:26
       
    
       
  
 
    
SUB SortArrDescend(ArrPointer AS LONG PTR, ArrLen AS LONG ) EXPORT
    DIM CurrentPos AS LONG
    DIM LocalArr () AS LONG
    REDIM LocalArr (1:ArrLen) AS LONG
    FOR CurrentPos = 0 TO ArrLen - 1
        LocalArr(CurrentPos)= @ArrPointer[CurrentPos]
    NEXT CurrentPos
    ARRAY SORT LocalArr& ), DESCEND
), DESCEND
END SUB
И когда вызываю её из VB
  im ArrPtr As Long
im ArrPtr As Long
 ArrPtr = VarPtrArray(Arr())
 SORTARRDESCEND ArrPtr, 1001
Массив остаётся несортированым.
		
	  
			 
	
		 
    
       
    
Номер ответа: 4 
      
Автор ответа: cresta
 cresta


Вопросов: 117
Ответов: 1538
      
 Профиль |  | #4
       
Добавлено:  23.01.04 22:32
       
    
       
  
Может дело в том, что в ПБ указатель имеет свой тип данных PTR, и восстанавливает массив через такой тип указателя, а в ВБ его нет и приходится передавать просто лонг
 
    
		
	  
			 
	
		 
    
       
    
Номер ответа: 5 
      
Автор ответа: Sharp
 Sharp










Лидер форума
ICQ: 216865379 
Вопросов: 106
Ответов: 9979
      
 Web-сайт:  
 Профиль |  | #5
      
Добавлено:  23.01.04 22:35
       
    
       
  
 
    
Насколько я понимаю, передавая так аргументы, ты реально передаешь указатель на ArrPtr (на указатель) и указатель на 1001 (не знаю, какого типа, наверно, Integer), а надо
		
	  
			 
	
		 
    
       
    
Номер ответа: 6 
      
Автор ответа: cresta
 cresta


Вопросов: 117
Ответов: 1538
      
 Профиль |  | #6
       
Добавлено:  23.01.04 23:46
       
    
       
  
 
    
		
	  
			 
	
		 
    
       
    
Номер ответа: 7 
      
Автор ответа: Sharp
 Sharp










Лидер форума
ICQ: 216865379 
Вопросов: 106
Ответов: 9979
      
 Web-сайт:  
 Профиль |  | #7
      
Добавлено:  23.01.04 23:59
       
    
       
  
Не падай духом! Сохраняй свой массив в файл, открывай его DLLей, сортируй и сохраняй обратно. А вообще, используй QuickSort, он работает настолько быстро, что тебе и DLL не придется писать.
 
    
		
	  
			 
	
		 
    
       
    
Номер ответа: 8 
      
Автор ответа: CyRax
 CyRax 




Разработчик Offline Client
ICQ: 204447456 
Вопросов: 180
Ответов: 4229
      
 Web-сайт:  
 Профиль |  | #8
      
Добавлено:  24.01.04 00:42
       
    
       
  
Держи! Хоть и сам помучался зато знаю теперь как это делать. 
    
===
-VB-
Private Declare Function GetArray Lib "DllArray.DLL" (MyArray As Long, Index As Integer) As Long
Private Sub Form_Load()
Dim Arr1(10) As Long
Arr1(0) = 0
For FillArr1 = 1 To 10: Arr1(FillArr1) = Arr1(FillArr1 - 1) + 100:  Next FillArr1
x = GetArray(Arr1(0), 9)
End Sub
----------------------------
-PBDLL-
Function GetArray Alias "GetArray"(MyArray As Long,Index As Integer) Export As Long
Dim xPtr As Long Pointer
xPtr = VarPtr(MyArray)
MsgBox Str$(@xPtr[Index])
End Function
		
	  
			 
	
		 
    
       
    
Номер ответа: 9 
      
Автор ответа: Sharp
 Sharp










Лидер форума
ICQ: 216865379 
Вопросов: 106
Ответов: 9979
      
 Web-сайт:  
 Профиль |  | #9
      
Добавлено:  24.01.04 00:59
       
    
       
  
 
    
		
	  
			 
	
		 
    
       
    
Номер ответа: 10 
      
Автор ответа: CyRax
 CyRax 




Разработчик Offline Client
ICQ: 204447456 
Вопросов: 180
Ответов: 4229
      
 Web-сайт:  
 Профиль |  | #10
      
Добавлено:  24.01.04 01:10
       
    
       
  
 
    
		
	  
			 
	
		 
    
       
    
Номер ответа: 11 
      
Автор ответа: CyRax
 CyRax 




Разработчик Offline Client
ICQ: 204447456 
Вопросов: 180
Ответов: 4229
      
 Web-сайт:  
 Профиль |  | #11
      
Добавлено:  24.01.04 01:12
       
    
       
  
А вообще, если ты земетил, кроме тебя уже все его начали изучать.
 
    
		
	  
			 
	
		 
    
       
    
Номер ответа: 12 
      
Автор ответа: Sharp
 Sharp










Лидер форума
ICQ: 216865379 
Вопросов: 106
Ответов: 9979
      
 Web-сайт:  
 Профиль |  | #12
      
Добавлено:  24.01.04 01:28
       
    
       
  
 
    
 ))
))
		
	  
			 
	
		 
    
       
    
Номер ответа: 13 
      
Автор ответа: sne
 sne





Разработчик Offline Client
ICQ: 233286456 
Вопросов: 34
Ответов: 5445
      
 Web-сайт:  
 Профиль |  | #13
      
Добавлено:  24.01.04 01:35
       
    
       
  
 
     )) Шучу
)) Шучу 
Держи руку помощи, надеюсь что не зря 20 мин. потратил, и хоть чем-то да помогу...
Код для VB:Option Explicit
Private Declare Sub CopyMemory Lib "kernel32.dll" Alias "RtlMoveMemory" (Destination As Any, Source As Any, ByVal Length As Long)
    Dim i As Long, MyArr() As Long
    
    ReDim MyArr(3)
    
    For i = 0 To UBound(MyArr)
        MyArr(i) = Rnd(Timer) * 100
        Call MsgBox(MyArr(i))
    Next
    Dim out As Long
    Call CopyMemory(out, MyArr(0), (UBound(MyArr) + 1&) * Len(MyArr(0)))
    Call GetArray(out, UBound(MyArr) + 1&)
End Sub
Код для PB:
#Compile Dll "New.dll"
#Include "Win32Api.inc"
                             ByVal iCnt   As Long) Export       ' Кол-во элементов
    ReDim Arr(iCnt - 1&)                                        ' Ресайзим его
    For i = 0 To iCnt - 1&
        MsgBox("Получено: " & Str$(Arr(i)))
    Next
 Вот еще вариант... Видать почти зазря тут пол-часа сидел...
		
	  
			 
	
		 
    
       
    
Номер ответа: 14 
      
Автор ответа: cresta
 cresta


Вопросов: 117
Ответов: 1538
      
 Профиль |  | #14
       
Добавлено:  24.01.04 01:58
       
    
       
  
 
     сколько всего сразу!!!!!!! Это всё мне???   Ну, спасибо всем!  Как говорили раньше, растроган до глубины души, блин. Спасибо ещё раз всем
сколько всего сразу!!!!!!! Это всё мне???   Ну, спасибо всем!  Как говорили раньше, растроган до глубины души, блин. Спасибо ещё раз всем . Буду ковырять...
. Буду ковырять...
		
	  
			 
	
		 
    
       
    
Номер ответа: 15 
      
Автор ответа: cresta
 cresta


Вопросов: 117
Ответов: 1538
      
 Профиль |  | #15
       
Добавлено:  24.01.04 06:42
       
    
       
  
Короче, вот что я наковырял за ночь: как предлагал Cyrax, я раньше делал, но результата не было, по его наводке стал тыкать везде msgbox  и всё прояснилось: указателем массив передать можно, он сортируется, но результатами сортировки не воспользуешься, т.к. массив при этом съезжает в сторону, и xPTR сортированного массива не совпадает с исходным... возвращать его в VB смысла нет, массив собрать нечем, поэтому добавил как Sne предложил, внутри DLL MoveMemory, стало сортировать и перемещать на место, вроде заработало, но почему-то при массивах больше 1000 элементов IDE падает, видимо MoveMemory наезжает на чужую область памяти. А до 1000 всё работает. И ещё: указатели на один и тот же массив из ПБ и через VarPtrArray изVB возвращают разные значения. Это так на заметку...