On Thursday, 27 February 2020 at 15:48:53 UTC, bachmeier wrote:
On Thursday, 27 February 2020 at 14:15:26 UTC, p.shkadzko wrote:
[...]
This works but it does not look very efficient considering we
flatten and then calling array twice. It will get even worse
with 3D arrays. Is there a better way without relying on
mir.ndslice?
Is there a reason you can't create a struct around a double[]
like this?
struct Matrix {
double[] data;
}
Then to add Matrix A to Matrix B, you use A.data[] + B.data[].
But since I'm not sure what exactly you're doing, maybe that
won't work.
Right! Ok, here is how I do it.
```
struct Matrix(T)
{
T[] elems;
int cols;
T[][] to2D()
{
return elems.chunks(cols).array;
}
}
```
and Matrix summing and random array generator functions
```
auto matrixSum(Matrix!int m1, Matrix!int m2)
{
Matrix!int m3;
m3.cols = m1.cols;
m3.elems.length = m1.elems.length;
m3.elems[] = m1.elems[] + m2.elems[];
return m3.to2D;
}
static T[] rndArr(T)(in T max, in int elems)
{
Xorshift rnd;
return generate(() => uniform(0, max, rnd)).take(elems).array;
}
```
Then we do the following
```
auto m1 = Matrix!int(rndArr!int(10, 5000 * 6000), 6000);
auto m2 = Matrix!int(rndArr!int(10, 5000 * 6000), 6000);
auto m3 = matrixSum(m1, m2);
```
And it works effortlessly!
Sum of two 5000 x 6000 int arrays is just 0.105 sec! (on a
Windows machine though but with weaker CPU).
I bet using mir.ndslice instead of D arrays would be even faster.