## digitalmars.D.learn - multidimensional array setting/slicing?

• Saaa (11/11) Jul 26 2008 Is there a easy way to set/read a multidimensional slice of an array?
• Rakan Alhneiti (13/30) Jul 26 2008 I dont think you can do this in any programming language not just D.
• Steven Schveighoffer (13/38) Jul 26 2008 Probably done easiest with a foreach loop:
• Steven Schveighoffer (4/40) Jul 26 2008 err.. that should have been
• Saaa (45/45) Jul 27 2008 Thanks, the code now looks like this (and works :)
• Steven Schveighoffer (21/66) Jul 28 2008 You can comment out these lines:
• bearophile (20/27) Jul 28 2008 There's this syntax too, if you remember the order of the sizes:
• Jarrett Billingsley (4/14) Jul 28 2008 Don't you think you're being a bit pedantic? Whitespace is optional and...
• bearophile (4/5) Jul 26 2008 I think in NumPy you can do similar things (and maybe in matlab too).
• BCS (2/7) Jul 27 2008 yes in matlab.
"Saaa" <empty needmail.com> writes:
```Is there a easy way to set/read a multidimensional slice of an array?

I'd like to do something like this... :)

int array[][];
array.length=100;
array[].length=200; :  Error: slice expression array[] is not a modifiable
lvalue

int array2[][];
array2.length=4;
array2[].length=2;
array2=[[1,2,3,4],[5,6,7,8]];

array[10..10+array2.length][150..150+array2[].length]=array2;
```
Jul 26 2008
Rakan Alhneiti <rakan.alhneiti nospam.gmail.com> writes:
```Saaa wrote:
Is there a easy way to set/read a multidimensional slice of an array?

I'd like to do something like this... :)

int array[][];
array.length=100;
array[].length=200; :  Error: slice expression array[] is not a modifiable
lvalue

int array2[][];
array2.length=4;
array2[].length=2;
array2=[[1,2,3,4],[5,6,7,8]];

array[10..10+array2.length][150..150+array2[].length]=array2;

I dont think you can do this in any programming language not just D.
Initialization of inner arrays in multidimensional arrays is done most
of the type using loops
int array[][];
array.length = 100;
for(int i = 0;i<array.length;i++)
{
array[i].length = 4;
}

as for slicing, i guess you will have to specify the starting and ending
index.
array2 = array1[0..5];
```
Jul 26 2008
"Steven Schveighoffer" <schveiguy yahoo.com> writes:
```"Rakan Alhneiti" wrote
Saaa wrote:
Is there a easy way to set/read a multidimensional slice of an array?

I'd like to do something like this... :)

int array[][];
array.length=100;
array[].length=200; :  Error: slice expression array[] is not a
modifiable lvalue

int array2[][];
array2.length=4;
array2[].length=2;
array2=[[1,2,3,4],[5,6,7,8]];

array[10..10+array2.length][150..150+array2[].length]=array2;

I dont think you can do this in any programming language not just D.
Initialization of inner arrays in multidimensional arrays is done most of
the type using loops
int array[][];
array.length = 100;
for(int i = 0;i<array.length;i++)
{
array[i].length = 4;
}

Probably done easiest with a foreach loop:

foreach(ref a; array)
a.length = 4;

The slicing is somthing that would have to be done using loops.

you might not realize, but a multi-dimensional dynamic array is really an
array of pointers, not one contiguous block of memory.  So each sub-array
points to a different memory space, and could have different lengths.

a loop with foreach would look something like:

foreach(i, ref a; array[10..10+array2.length])
a[] = array2[i];

Probably other ways to do it.

-Steve
```
Jul 26 2008
"Steven Schveighoffer" <schveiguy yahoo.com> writes:
```"Steven Schveighoffer" wrote
"Rakan Alhneiti" wrote
Saaa wrote:
Is there a easy way to set/read a multidimensional slice of an array?

I'd like to do something like this... :)

int array[][];
array.length=100;
array[].length=200; :  Error: slice expression array[] is not a
modifiable lvalue

int array2[][];
array2.length=4;
array2[].length=2;
array2=[[1,2,3,4],[5,6,7,8]];

array[10..10+array2.length][150..150+array2[].length]=array2;

I dont think you can do this in any programming language not just D.
Initialization of inner arrays in multidimensional arrays is done most of
the type using loops
int array[][];
array.length = 100;
for(int i = 0;i<array.length;i++)
{
array[i].length = 4;
}

Probably done easiest with a foreach loop:

foreach(ref a; array)
a.length = 4;

The slicing is somthing that would have to be done using loops.

you might not realize, but a multi-dimensional dynamic array is really an
array of pointers, not one contiguous block of memory.  So each sub-array
points to a different memory space, and could have different lengths.

a loop with foreach would look something like:

foreach(i, ref a; array[10..10+array2.length])
a[] = array2[i];

err.. that should have been
a[150..150+array2[i].length] = array2[i];

-Steve
```
Jul 26 2008
"Saaa" <empty needmail.com> writes:
```Thanks, the code now looks like this (and works :)

int array[][];
array.length=10;
foreach(ref a; array)
a.length = 5;

int array2[][];
array2.length=2;
foreach(ref a; array)
a.length = 6;

array2=[[1,2,3,4],[5,6,7,8]];

foreach(i, ref a; array[2..2+array2.length])
a[1..1+array2[i].length] = array2[i];

writefln(array2);
writefln(array);

[[1,2,3,4],[5,6,7,8]]
[[0,0,0,0,0,0],[0,0,0,0,0,0],[0,1,2,3,4,0],[0,5,6,7,8,0],[0,0,0,0,0,0],
[0,0,0,0,0,0],[0,0,0,0,0,0],[0,0,0,0,0,0],[0,0,0,0,0,0],[0,0,0,0,0,0]]
--------------------------
//And for 3D:

int array[][][];
array.length=6;
foreach(ref a; array)
{
a.length = 6;
foreach(ref b; a)
b.length = 6;
}

int array2[][][];
array2.length=2;
foreach(ref a; array2)
{
a.length = 2;
foreach(ref b; a)
b.length = 2;
}

array2=[[[1,2],[5,6]],[[9,9],[8,7]]];

foreach(i, ref a; array[2..2+array2.length])
foreach(ii, ref b; a[2..2+array2[0].length])
b[1..1+array2[ii].length] = array2[i][ii];

writefln(array2);
writefln(array);
--------------------------
... erm I barely follow it myself :/

I think array can be static and maybe array2 will be as well and I'll
manually keep the x,y and z sizes and do normal for-loops over them.
```
Jul 27 2008
"Steven Schveighoffer" <schveiguy yahoo.com> writes:
```"Saaa" wrote
Thanks, the code now looks like this (and works :)

int array[][];
array.length=10;
foreach(ref a; array)
a.length = 5;

int array2[][];

You can comment out these lines:

/*
array2.length=2;
foreach(ref a; array)
a.length = 6;

*/

array2=[[1,2,3,4],[5,6,7,8]];

could be:

auto array2=[[1,2,3,4],[5,6,7,8]];

and get rid of the array2 declaration above.

At this point, you have thrown away all your work you did to set the lengths
in array2 :)

Note that setting array2 this way just changes the array to point to the
array literal, it doesn't copy data from the literal.

foreach(i, ref a; array[2..2+array2.length])
a[1..1+array2[i].length] = array2[i];

writefln(array2);
writefln(array);

[[1,2,3,4],[5,6,7,8]]
[[0,0,0,0,0,0],[0,0,0,0,0,0],[0,1,2,3,4,0],[0,5,6,7,8,0],[0,0,0,0,0,0],
[0,0,0,0,0,0],[0,0,0,0,0,0],[0,0,0,0,0,0],[0,0,0,0,0,0],[0,0,0,0,0,0]]
--------------------------
//And for 3D:

int array[][][];
array.length=6;
foreach(ref a; array)
{
a.length = 6;
foreach(ref b; a)
b.length = 6;
}

int array2[][][];

ditto here:
/*
array2.length=2;
foreach(ref a; array2)
{
a.length = 2;
foreach(ref b; a)
b.length = 2;
}

*/

array2=[[[1,2],[5,6]],[[9,9],[8,7]]];

could be:

auto array2=[[[1,2],[5,6]],[[9,9],[8,7]]];

foreach(i, ref a; array[2..2+array2.length])
foreach(ii, ref b; a[2..2+array2[0].length])
b[1..1+array2[ii].length] = array2[i][ii];

writefln(array2);
writefln(array);
--------------------------
... erm I barely follow it myself :/

Yeah, it's not really that readable :)  Perhaps encapsulating it into a

I think array can be static and maybe array2 will be as well and I'll
manually keep the x,y and z sizes and do normal for-loops over them.

static arrays are different than dynamic arrays, in that they are contiguous
memory :)  But I think you will still need to set the data in the same way.

-Steve
```
Jul 28 2008
bearophile <bearophileHUGS lycos.com> writes:
```Saaa Wrote:
... erm I barely follow it myself :/

There are ways to shorten your code a little, and/or to make it a bit more
readable. You have to learn still where to put spaces too.

int array[][];
array.length=10;
foreach(ref a; array)
a.length = 5;

There's this syntax too, if you remember the order of the sizes:
auto array = new int[][][](n1, n2, n3);

foreach(ref a; array)
=>
foreach (ref a; array)

a[1..1+array2[i].length] = array2[i];

=>
a[1 .. 1+array2[i].length] = array2[i];

array2.length=2;
=>
array2.length = 2;

In some situations you can use \$ instead of length (but not in the code you
have shown, I think).
And you can write yourself a slice(...) function able to perform your complex
slices reducing syntax clutter (but it doesn't support the .. operator, sadly,
as in the .../: of python).

Note that this:
auto a = [[1, 2], [3, 4]];
Isn't the same thing as:
int[][] a = [[1, 2], [3, 4]];
If you use auto the compiler chooses to use a static array.

Bye,
bearophile
```
Jul 28 2008
"Jarrett Billingsley" <kb3ctd2 yahoo.com> writes:
```"bearophile" <bearophileHUGS lycos.com> wrote in message
news:g6kn24\$77v\$1 digitalmars.com...

You have to learn still where to put spaces too.

foreach(ref a; array)
=>
foreach (ref a; array)

a[1..1+array2[i].length] = array2[i];

=>
a[1 .. 1+array2[i].length] = array2[i];

array2.length=2;
=>
array2.length = 2;

Don't you think you're being a bit pedantic?  Whitespace is optional and
everyone has their own preferences.
```
Jul 28 2008
bearophile <bearophileHUGS lycos.com> writes:
```Rakan Alhneiti:
I dont think you can do this in any programming language not just D.

I think in NumPy you can do similar things (and maybe in matlab too).

Bye,
bearophile
```
Jul 26 2008
```Reply to bearophile,