EnableExplicit Procedure.i GetStringArray(*pSA.i, Count.i, Array List.s(1)) Define.i i If Count = 0 Define.i pSA = PeekI(*pSA); Count = PeekI(pSA+16); pSA = PeekI(pSA+12); ReDim List(Count) For i = 0 To Count -1 List(i) = PeekS(PeekI(pSA+i*4)) Next Else ReDim List(Count) For i = 0 To Count -1 List(i) = PeekS(*pSA + 24 * i) Next EndIf ProcedureReturn Count EndProcedure ProcedureDLL Show_StringArray(*pSA, Count.i = 0) Dim List.s(0) Count.i = GetStringArray(*pSA, Count, List()) Define i Define Sentence.s = "" For i = 0 To Count -1 Sentence = Sentence + List(i) + #CRLF$ Next MessageRequester(Str(Count) + " elements", Sentence) EndProcedure ; Dim xsPlanets.s(8) ; xsPlanets(0) = "Mercure" ; xsPlanets(1) = "Venus" ; xsPlanets(2) = "Terre" ; xsPlanets(3) = "Mars" ; xsPlanets(4) = "Jupiter" ; xsPlanets(5) = "Saturne" ; xsPlanets(6) = "Uranus" ; xsPlanets(7) = "Neptune" ; Show_StringArray(@xsPlanets(0), 8)
EnableExplicit Prototype Show_StringArray(*pFirst.i, Count.i) Define LIB_TheDLL.i = OpenLibrary(#PB_Any, "TheDll") If LIB_TheDLL Define Show_StringArray_.Show_StringArray = GetFunction(LIB_TheDLL, "Show_StringArray") EndIf Macro Show_StringArray(x) Show_StringArray_(@x#(0), ArraySize(x#())) EndMacro Dim xsPlanets.s(8) xsPlanets(0) = "Mercure" xsPlanets(1) = "Venus" xsPlanets(2) = "Terre" xsPlanets(3) = "Mars" xsPlanets(4) = "Jupiter" xsPlanets(5) = "Saturne" xsPlanets(6) = "Uranus" xsPlanets(7) = "Neptune" Show_StringArray(xsPlanets)
Private Declare Sub Show_StringArray Lib "TheDll" (ByRef vxsData() As String, Optional ByVal vnCount As Long = 0) Sub Main() Dim xsPlanets(7) As String xsPlanets(0) = "Mercure" xsPlanets(1) = "Venus" xsPlanets(2) = "Terre" xsPlanets(3) = "Mars" xsPlanets(4) = "Jupiter" xsPlanets(5) = "Saturne" xsPlanets(6) = "Uranus" xsPlanets(7) = "Neptune" Show_StringArray xsPlanets End Sub
Type maStructure myArray(10) As String) End Type
Vous n’avez pas trouvé la réponse que vous recherchez ?
Posez votre questionSalut Eric, comment est déclaré ArrayStruct ?
que contient cette Structure ?
For i = 1 To UBound(TheArray())
cette manie de commencer à 1....
tu peux lui filer des pointeurs vers tes String, elles pourront être manipulées par ta dll PB
Function BSTRtoLPSTR(sBSTR As String, b() As Byte, lpsz As Long) As Long ' Input: a nonempty BSTR string ' Input: **undimensioned** byte array b() ' Output: Fills byte array b() with ANSI char string ' Output: Fills lpsz with a pointer to b() array ' Returns byte count, not including terminating null ' Original BSTR is not affected Dim cBytes As Long Dim sABSTR As String cBytes = LenB(sBSTR) ' ReDim array, with space for terminating null ReDim b(1 To cBytes + 2) As Byte ' Convert to ANSI sABSTR = StrConv(sBSTR, vbFromUnicode) ' Point to BSTR char array lpsz = StrPtr(sABSTR) ' Copy the array CopyMemory b(1), ByVal lpsz, cBytes + 2 ' Point lpsz to new array lpsz = VarPtr(b(1)) ' Return byte count BSTRtoLPSTR = cBytes End Function
Private Declare Function HeapAlloc Lib "kernel32" (ByVal hHeap As Long, ByVal dwFlags As Long, ByVal dwBytes As Long) As Long Private Declare Function HeapFree Lib "kernel32" (ByVal hHeap As Long, ByVal dwFlags As Long, lpMem As Any) As Long Private Declare Function GetProcessHeap Lib "kernel32" () As Long Private Declare Sub CopyMemoryWrite Lib "kernel32" Alias "RtlMoveMemory" (Destination As Long, ByVal Source As String, ByVal Length As Long) Private Declare Sub ShowArrayString Lib "C:\Travail\Allocation mémoire libérée par la DLL [Kcc]\TheDll.dll" (ByRef ArrayPtr As ArrayStruct) Private Declare Sub CopyMemory Lib "kernel32" Alias "RtlMoveMemory" (b As Any, lpsz As Long, cBytes As Long) Private Sub Form_Load() Dim TheArray(10) As String Dim ArrayString As ArrayStruct Dim ArrayLen As Integer Dim OffsetPtr As Long Dim hHeap As Long ChDir App.Path CurDir Left(App.Path, 3) For i = 1 To UBound(TheArray()) TheArray(i) = "Sentence n° " + Str(i) ArrayLen = ArrayLen + Len("Sentence n° " + Str(i)) Next Dim b() As Byte Dim lpsz As Long, lng As Long, Lpstr As Long ArrayString.Size = UBound(TheArray()) hHeap = GetProcessHeap() ArrayString.Ptr = HeapAlloc(hHeap, 0, ArrayLen) OffsetPtr = ArrayString.Ptr For i = 1 To UBound(TheArray()) Lpstr = BSTRtoLPSTR(TheArray(i), b, lpsz) CopyMemoryWrite OffsetPtr, Lpstr, 4 OffsetPtr = OffsetPtr + LenB(ArrayAscii) Next ShowArrayString ArrayString HeapFree GetProcessHeap(), 0, ArrayString.Ptr End Sub Function BSTRtoLPSTR(sBSTR As String, b() As Byte, lpsz As Long) As Long ' Input: a nonempty BSTR string ' Input: **undimensioned** byte array b() ' Output: Fills byte array b() with ANSI char string ' Output: Fills lpsz with a pointer to b() array ' Returns byte count, not including terminating null ' Original BSTR is not affected Dim cBytes As Long Dim sABSTR As String cBytes = LenB(sBSTR) ' ReDim array, with space for terminating null ReDim b(1 To cBytes + 2) As Byte ' Convert to ANSI sABSTR = StrConv(sBSTR, vbFromUnicode) ' Point to BSTR char array lpsz = StrPtr(sABSTR) ' Copy the array CopyMemory b(1), ByVal lpsz, cBytes + 2 ' Point lpsz to new array lpsz = VarPtr(b(1)) ' Return byte count BSTRtoLPSTR = cBytes End Function
Type ArrayStruct Ptr As Long Size As Integer End Type
Structure ArrayStruct *Ptr.l Size.i EndStructure ProcedureDLL ShowArrayString(*TheArray.ArrayStruct) *OffsetPtr = *TheArray\Ptr For i = 1 To *TheArray\Size String$ = PeekS(*OffsetPtr,4) SentenceString$ + String$ + Chr(13) *OffsetPtr + Len(String$) + 1 Next FreeMemory(*TheArray); <=== Ai je le droit ??? MessageRequester("The array form EXE", SentenceString$) EndProcedure
Comme pour les tableaux ...
Non, même les tableaux peuvent etre liberés... suffit de bien lui demander.
pour la mémoire allouée, même topo...
bien lui demander et dans VB ne plus mentionner ce pointeur devenu invalide...
FreeMemory(*TheArray);
une raison particulière de donner une copie de cette structure, au final et non la structure allouée par VB ?