Passing Multi-Dimension Arrays from VB to DLL
Author |
Message |
Craig #1 / 5
|
 Passing Multi-Dimension Arrays from VB to DLL
Probably been asked before but... I'm coding an app in VB 6 with all the math intensive stuff handled by a C++ Builder 4 DLL The problem is I can't figure out how to pass multi dimension arrays by reference between the two. Single dimension arrays are no problem - Declare function foo lib "mylib.dll" (byref gk as single) as long Dim gk(4) as single i = foo( gk(0) ) long __stdcall foo ( float *gk ) { // do calcs with it gk[1] += 10; etc... So how do you go about passing a Dim gk(4,4) to it ? I know the solution's gonna be something simple... like me ;-) TIA,
|
Mon, 19 Jul 2004 03:07:36 GMT |
|
 |
Neila Nes #2 / 5
|
 Passing Multi-Dimension Arrays from VB to DLL
Hi Craig, This should get the juices going... I usually dim starting at 0 but using 1 in this case is easier to illustrate the memory mapping of one_dim to multi_dim arrays. HTH, Neila Option Explicit Private Declare Sub CopyMemory _ Lib "kernel32" _ Alias "RtlMoveMemory" _ (Destination As Any, _ Source As Any, _ ByVal Length As Long) Private Sub Private Sub ooo________ooo________ooo() Dim MDArray() As Double Dim OneDArray() As Double Dim i As Long Dim j As Long Dim k As Long Dim lCopySize As Long ReDim MDArray(1 To 3, 1 To 3, 1 To 3) '27 elements ReDim OneDArray(1 To 27) For i = 1 To 3 For j = 1 To 3 For k = 1 To 3 MDArray(i, j, k) = i * 100 + j * 10 + k Next 'k Next 'j Next 'i lCopySize = 27 * LenB(OneDArray(0)) Call CopyMemory(OneDArray(1), MDArray(1, 1, 1), ByVal lCopySize) For i = 1 To 27 Debug.Print OneDArray(i) Next End Sub 111 211 311 121 221 321 131 231 331 112 212 312 122 222 322 132 232 332 113 213 313 123 223 323 133 233 333 Quote:
> Probably been asked before but... > I'm coding an app in VB 6 with all the math intensive > stuff handled by a C++ Builder 4 DLL The problem is I > can't figure out how to pass multi dimension arrays by > reference between the two. > Single dimension arrays are no problem - > Declare function foo lib "mylib.dll" (byref gk as single) as long > Dim gk(4) as single > i = foo( gk(0) ) > long __stdcall foo ( float *gk ) > { // do calcs with it > gk[1] += 10; > etc... > So how do you go about passing a Dim gk(4,4) to it ? > I know the solution's gonna be something simple... > like me ;-) > TIA,
|
Mon, 19 Jul 2004 09:49:37 GMT |
|
 |
Brad Pan #3 / 5
|
 Passing Multi-Dimension Arrays from VB to DLL
As you have found out VB and VC have opposite array ordering, one is Row, Column and the other is Column, Row. When I passed a 2 dimensional routine I spent quite a few days working on a routine to get them back in the same order, and I ended up padding the array out with each dimension the same 10X10 to get it to work right. Instead of spending days working this out, I would pass the array one dimension at a time and just do multiple calls. You may also want to check out SafeArrays which "I think" may support this better. Quote:
> Hi Craig, > This should get the juices going... > I usually dim starting at 0 but using 1 in this case is easier to > illustrate the memory mapping of one_dim to multi_dim arrays. > HTH, Neila > Option Explicit > Private Declare Sub CopyMemory _ > Lib "kernel32" _ > Alias "RtlMoveMemory" _ > (Destination As Any, _ > Source As Any, _ > ByVal Length As Long) > Private Sub Private Sub ooo________ooo________ooo() > Dim MDArray() As Double > Dim OneDArray() As Double > Dim i As Long > Dim j As Long > Dim k As Long > Dim lCopySize As Long > ReDim MDArray(1 To 3, 1 To 3, 1 To 3) '27 elements > ReDim OneDArray(1 To 27) > For i = 1 To 3 > For j = 1 To 3 > For k = 1 To 3 > MDArray(i, j, k) = i * 100 + j * 10 + k > Next 'k > Next 'j > Next 'i > lCopySize = 27 * LenB(OneDArray(0)) > Call CopyMemory(OneDArray(1), MDArray(1, 1, 1), ByVal lCopySize) > For i = 1 To 27 > Debug.Print OneDArray(i) > Next > End Sub > 111 > 211 > 311 > 121 > 221 > 321 > 131 > 231 > 331 > 112 > 212 > 312 > 122 > 222 > 322 > 132 > 232 > 332 > 113 > 213 > 313 > 123 > 223 > 323 > 133 > 233 > 333
> > Probably been asked before but... > > I'm coding an app in VB 6 with all the math intensive > > stuff handled by a C++ Builder 4 DLL The problem is I > > can't figure out how to pass multi dimension arrays by > > reference between the two. > > Single dimension arrays are no problem - > > Declare function foo lib "mylib.dll" (byref gk as single) as long > > Dim gk(4) as single > > i = foo( gk(0) ) > > long __stdcall foo ( float *gk ) > > { // do calcs with it > > gk[1] += 10; > > etc... > > So how do you go about passing a Dim gk(4,4) to it ? > > I know the solution's gonna be something simple... > > like me ;-) > > TIA,
|
Mon, 19 Jul 2004 22:32:26 GMT |
|
 |
Craig #4 / 5
|
 Passing Multi-Dimension Arrays from VB to DLL
Quote: > This should get the juices going... > I usually dim starting at 0 but using 1 in this case is easier to > illustrate the memory mapping of one_dim to multi_dim arrays. > HTH, Neila > Option Explicit > Private Declare Sub CopyMemory _ > Lib "kernel32" _ > Alias "RtlMoveMemory" _
<snip> Hi, I managed to convert some of my code to use this technique. Unfortunately, there's just too much overhead and the array indexing slows it up by quite a bit, it looks as tho' I'm gonna have to seriously re-think the code :-(. Anyway, many thanks for the reply, much appreciated :)
|
Wed, 21 Jul 2004 03:32:39 GMT |
|
 |
J Fren #5 / 5
|
 Passing Multi-Dimension Arrays from VB to DLL
On Fri, 1 Feb 2002 19:32:39 -0000, "Craig W"
_ Quote: ><snip> >Hi, I managed to convert some of my code to use this >technique. Unfortunately, there's just too much overhead and >the array indexing slows it up by quite a bit, it looks as tho' >I'm gonna have to seriously re-think the code :-(. >Anyway, many thanks for the reply, much appreciated :)
I assume that you are using the CPP DLL for speed, and that the VB bit is, well not so speed critical. An array is just a block of memory - you could 'front' your VB Array with properties that access a block of memory in the CPP format. That way you appear to have a VB array - in VB format If you pre-calculate the offsets and hold them in an array of Longs then there should be little overhead at the VB end. Of course this pre-supposes that you make minor changes to the VB Array and repeatedly call the CPP DLL to recalculate. An even better method would be, assuming you have the source of the DLL, to 'embed' the VB array in the CPP DLL - or maybe a 'driver' DLL
|
Wed, 21 Jul 2004 17:04:53 GMT |
|
|
|