adamski

Solved: Syntax to populate an Array

19 posts in this topic

#1 ·  Posted (edited)

Hello,

I need to fill a 2d array with values. I have been using the code:

; Array Size
Local $NumRows = 5
Local $NumColumns = 7

Local $MyArray[$NumRows ][$NumColumns] = [["one1",  "two1", "three1",   "four1",    "five1",    "six1", "seven1"], _
 ["one2",   "two2", "three2",   "four2",    "five2",    "six2", "seven2"], _
 ["one3",   "two3", "three3",   "four3",    "five3",    "six3", "seven3"], _
 ["one4",   "two4", "three4",   "four4",    "five4",    "six4", "seven4"], _
 ["one5",   "two5", "three5",   "four5",    "five5",    "six5", "seven5"]]

This is fine until I need to have $NumRows = 267.

At this size I get errors which I'm guessing is due to the length of the 'line' of code.

Is there another way to define the elements of a 2d array other than setting each element individually?

Thanks.

Edited by adamski

Share this post


Link to post
Share on other sites



You're not using the latest autoit are you!!! That line limit has now been removed.

Anyhow. You want 2 for loops inside each other. Something like this:

For $x = 0 To $NumRows - 1
    For $y = 0 To $NumColumns - 1
        $MyArray[$x][$y] = $x & ", " & $y
    Next
Next

Share this post


Link to post
Share on other sites

Ah right - not used AutoIt for a while. I'll update.

I can't loop since the data I'm putting in is arbitrary not calculatable (I posted example data).

Cheers

Share this post


Link to post
Share on other sites

Same problem with the newest version :D.

Any other suggestions?

Share this post


Link to post
Share on other sites

Same problem with the newest version :D.

Any other suggestions?

Yes, do each line individually eg:

Global $a_array[5][4]
$a_array[0][0] = "something"
$a_array[0][1] = "something"
;etc
$a_array[1][0] = "something"
$a_array[1][1] = "something"
;etc

[center]Common sense plays a role in the basics of understanding AutoIt... If you're lacking in that, do us all a favor, and step away from the computer.[/center]

Share this post


Link to post
Share on other sites

Same problem with the newest version :D.

Any other suggestions?

Then go try the latest _beta_ version (3.3.3.3), which works fine (just checked). If it doesn't work for you, then you have a syntax error somewhere or anoher problem unrelated with input line length.

This wonderful site allows debugging and testing regular expressions (many flavors available). An absolute must have in your bookmarks.
Another excellent RegExp tutorial. Don't forget downloading your copy of up-to-date pcretest.exe and pcregrep.exe here
RegExp tutorial: enough to get started
PCRE v8.33 regexp documentation latest available release and currently implemented in AutoIt beta.

SQLitespeed is another feature-rich premier SQLite manager (includes import/export). Well worth a try.
SQLite Expert (freeware Personal Edition or payware Pro version) is a very useful SQLite database manager.
An excellent eBook covering almost every aspect of SQLite3: a must-read for anyone doing serious work.
SQL tutorial (covers "generic" SQL, but most of it applies to SQLite as well)
A work-in-progress SQLite3 tutorial. Don't miss other LxyzTHW pages!
SQLite official website with full documentation (may be newer than the SQLite library that comes standard with AutoIt)

Share this post


Link to post
Share on other sites

#7 ·  Posted (edited)

Based on the data you have given, I would write something like the following:

#include <Array.au3>

Local $MyArray[5][7], $data, $skip

$data = "one1two1three1four1five1six1seven1" &  _
"one2two2three2four2five2six2seven2" &  _
"one3two3three3four3five3six3seven3" & _
"one4two4three4four4five4six4seven4" & _
"one5two5three5four5five5six5seven5"

$skip = "4465546"
$k = 1
For $i = 0 To 4
    For $j = 0 To 6
        $MyArray[$i][$j] = StringMid($data, $k, StringMid($skip, $j +1, 1))
        $k += StringMid($skip, $j +1, 1)
    Next
Next
_ArrayDisplay($MyArray)

This relys on the fact that each row contains similar data. The length of each data string is identified by the pattern $skip.

Edited by czardas

Share this post


Link to post
Share on other sites

This relys on the fact that each row contains similar data. The length of each data string is identified by the pattern $skip.

The OP already made clear his actual data didn't have such a pattern.

This wonderful site allows debugging and testing regular expressions (many flavors available). An absolute must have in your bookmarks.
Another excellent RegExp tutorial. Don't forget downloading your copy of up-to-date pcretest.exe and pcregrep.exe here
RegExp tutorial: enough to get started
PCRE v8.33 regexp documentation latest available release and currently implemented in AutoIt beta.

SQLitespeed is another feature-rich premier SQLite manager (includes import/export). Well worth a try.
SQLite Expert (freeware Personal Edition or payware Pro version) is a very useful SQLite database manager.
An excellent eBook covering almost every aspect of SQLite3: a must-read for anyone doing serious work.
SQL tutorial (covers "generic" SQL, but most of it applies to SQLite as well)
A work-in-progress SQLite3 tutorial. Don't miss other LxyzTHW pages!
SQLite official website with full documentation (may be newer than the SQLite library that comes standard with AutoIt)

Share this post


Link to post
Share on other sites

#9 ·  Posted (edited)

The Beta versions since 3.3.3.2 no longer have any line limit where it is assembled with the "_" underscore. What version are you trying it with? The current production version 3.3.2.0 would get an error, but the later Betas would not.

:D

Edit: jchd said that already.

Edited by PsaltyDS

Valuater's AutoIt 1-2-3, Class... Is now in Session!For those who want somebody to write the script for them: RentACoder"Any technology distinguishable from magic is insufficiently advanced." -- Geek's corollary to Clarke's law

Share this post


Link to post
Share on other sites

That would be 267*7=1869 lines! Is there not even a way to set each row of 7 elements at once?

Share this post


Link to post
Share on other sites

#11 ·  Posted (edited)

The OP already made clear his actual data didn't have such a pattern.

You can write the pattern in full, or determine the data by a process. As I don't know the data the OP actually wants to put in the array, I can't determine the exact method. Edited by czardas

Share this post


Link to post
Share on other sites

That would be 267*7=1869 lines! Is there not even a way to set each row of 7 elements at once?

No, it would be 267 lines done as you had it in the OP. You could also assemble a string with whatever delimiters you liked and split it with your own function (ala czardas).

I posted a 2D array version of _ArrayConcatenate() a long time ago. You could search that up too.

The easiest way to do it would depend on the source of the data, and you haven't been clear about that.

:D


Valuater's AutoIt 1-2-3, Class... Is now in Session!For those who want somebody to write the script for them: RentACoder"Any technology distinguishable from magic is insufficiently advanced." -- Geek's corollary to Clarke's law

Share this post


Link to post
Share on other sites

This forum Moves fast!

PsaltyDS:

Iwas replying to SmOke_N with the last post before the other had appeared!

PsaltyDS & jchd:

Yes, you are correct. It works in the Beta. I thought I'd tried it but my "Toggle AU3 Beta" appears not to work. Maybe it's because I'm on a x64 machine.

The data has no pattern, but this is solved now - Thanks to all

Share this post


Link to post
Share on other sites

I wonder ... did you look at the code Mat posted for you???

That is the solution you need to use.

I cannot believe that all 1869 lines are "in your memory"; they are definitely stored in a file somewhere.

So, open that file, read the text (lines), make your script get the content in the correct order, populate ath array the way Mat showed you.

This is not a very easy script, the most complicated task will be to get the information "tailored".

Have a look at this demo script:

#include <array.au3>
Dim $MyDataARRAY[2][3]

$MyData1 = "one1,two1,three1"   ;these might be lines in a text file
$MyData2 = "one2,two2,three2"   ;these might be lines in a text file

$MyDataARR1 = StringSplit($MyData1, ",")    ;split them
For $x = 1 To $MyDataARR1[0]                ;fill the final array
    $MyDataARRAY[0][$x-1] = $MyDataARR1[$x]
Next

$MyDataARR2 = StringSplit($MyData2, ",")
For $x = 1 To $MyDataARR2[0]
    $MyDataARRAY[1][$x-1] = $MyDataARR2[$x]
Next

_ArrayDisplay($MyDataARRAY)

This script is only an example; something to get you started. Remember, when dealing with big arrays, For/Next is your best friend.

1 person likes this

SNMP_UDF ... for SNMPv1 and v2c so far, GetBulk and a new example script

wannabe "Unbeatable" Tic-Tac-Toe

Paper-Scissor-Rock ... try to beat it anyway :)

Share this post


Link to post
Share on other sites

#15 ·  Posted (edited)

Have a look at this demo script:

I also thought of using StringSplit. The method I gave produces the 2D array in one hit (as is the case in the original post), but it is limited to data strings up to 9 characters in length. To solve that I would need to represent the pattern in an array rather than using a string.

Adamski: When I say pattern, I don't necessarily mean a pattern that repeats. It could be an irregular pattern. Anyway I'm glad you sorted it out.

Edited by czardas

Share this post


Link to post
Share on other sites

#16 ·  Posted (edited)

My 2 cents!

I wrote this for pulling in data from a csv. - just took out the fileread()s

Can still be worked on.

Matt

#include <Array.au3>
$sData = "1,2,3,4,5" & @CRLF & "6,7,8,9,10" & @CRLF & "11,12,13,14,15" & @CRLF & "16,17,18,19,20" & @CRLF
Local $aTheArray[1][5]

_Populate($sData, $aTheArray)
_ArrayDisplay($aTheArray)

Func _Populate($sData, ByRef $aArray)
    Local $aData = StringSplit(StringStripCR($sData), "," & @LF, 2)
    ReDim $aArray[UBound($aData) / UBound($aArray, 2)][UBound($aArray, 2)]
    For $i = 0 To UBound($aData) - 2
        $aArray[Int($i / UBound($aArray, 2))][Mod($i, UBound($aArray, 2))] = $aData[$i]
    Next
EndFunc
Edited by MattyD
2 people like this

Share this post


Link to post
Share on other sites

Having read this:-

I also thought of using StringSplit. The method I gave produces the 2D array in one hit (as is the case in the original post), but it is limited to data strings up to 9 characters in length. To solve that I would need to represent the pattern in an array rather than using a string.

.............

I did this.

#include <Array.au3>

Local $MyArray[5][11], $data, $skip

$data = "one1two1three1four1five1six1seven1eight1nine1ten1eleven1" & _
        "one2two2three2four2five2six2seven2eight2nine2ten2eleven2" & _
        "one3two3three3four3five3six3seven3eight3nine3ten3eleven3" & _
        "one4two4three4four4five4six4seven4eight4nine4ten4eleven4" & _
        "one5two5three5four5five5six5seven5eight5nine5ten5eleven5"

Local $sPattern = '"(?:.*\d*)' & StringRegExpReplace(StringFormat("%" & UBound($MyArray, 2) & _
        "s", " "), ".", '([^\d]{3,10}" & ($i + 1) & ")') & '(?:\d*.*)"'
;ConsoleWrite($sPattern & @CRLF)

For $i = 0 To UBound($MyArray, 1) - 1
    For $j = 0 To UBound($MyArray, 2) - 1
        $MyArray[$i][$j] = StringRegExpReplace($data, Execute($sPattern), "${" & ($j + 1) & "}")
    Next
Next

_ArrayDisplay($MyArray)

Someone might get an idea from this example, maybe.

Share this post


Link to post
Share on other sites

Having read this:-

I did this.

#include <Array.au3>

Local $MyArray[5][11], $data, $skip

$data = "one1two1three1four1five1six1seven1eight1nine1ten1eleven1" & _
        "one2two2three2four2five2six2seven2eight2nine2ten2eleven2" & _
        "one3two3three3four3five3six3seven3eight3nine3ten3eleven3" & _
        "one4two4three4four4five4six4seven4eight4nine4ten4eleven4" & _
        "one5two5three5four5five5six5seven5eight5nine5ten5eleven5"

Local $sPattern = '"(?:.*\d*)' & StringRegExpReplace(StringFormat("%" & UBound($MyArray, 2) & _
        "s", " "), ".", '([^\d]{3,10}" & ($i + 1) & ")') & '(?:\d*.*)"'
;ConsoleWrite($sPattern & @CRLF)

For $i = 0 To UBound($MyArray, 1) - 1
    For $j = 0 To UBound($MyArray, 2) - 1
        $MyArray[$i][$j] = StringRegExpReplace($data, Execute($sPattern), "${" & ($j + 1) & "}")
    Next
Next

_ArrayDisplay($MyArray)

Someone might get an idea from this example, maybe.

Nice one! :D

Share this post


Link to post
Share on other sites

about if i want the data to be variable so they can represent value instead 

ie $b="123"

$sData = "$b,2,3,4,5" & @CRLF & "6,7,8,9,10" & @CRLF & "11,12,13,14,15" & @CRLF & "16,17,18,19,20" & @CRLF

#include <Array.au3>
$sData = "1,2,3,4,5" & @CRLF & "6,7,8,9,10" & @CRLF & "11,12,13,14,15" & @CRLF & "16,17,18,19,20" & @CRLF
Local $aTheArray[1][5]

_Populate($sData, $aTheArray)
_ArrayDisplay($aTheArray)

Func _Populate($sData, ByRef $aArray)
    Local $aData = StringSplit(StringStripCR($sData), "," & @LF, 2)
    ReDim $aArray[UBound($aData) / UBound($aArray, 2)][UBound($aArray, 2)]
    For $i = 0 To UBound($aData) - 2
        $aArray[Int($i / UBound($aArray, 2))][Mod($i, UBound($aArray, 2))] = $aData[$i]
    Next
EndFunc

 

Share this post


Link to post
Share on other sites

Create an account or sign in to comment

You need to be a member in order to leave a comment

Create an account

Sign up for a new account in our community. It's easy!


Register a new account

Sign in

Already have an account? Sign in here.


Sign In Now