0

I need to write a program that computes values in a matrix, first sequentially, then in parallel using openCL.

It is the same thing as I already did in regular C (using MPI)

I want to make simple functions to initializeMatrix and printMatrix and the likes.

In C i used to do this very simply :

// Matrix initialization
 void initMatrix(size_t M, size_t N, double (*matrix)[M][N][2])
{
    int i, j;
    for (j = 0; j < N; ++j)
    {
        for (i = 0; i < M; ++i)
        {
            (*matrix)[i][j][0] = (double)(( i * ( M - i - 1 ) ) * ( j * ( N - j - 1 ) ));
            (*matrix)[i][j][1] = (*matrix)[i][j][0];
        }
    }
    printf("Matrix has been initialized\n");
}

I saw this gets me errors in C++, as the compiler wants to know at COMPILE TIME the sizes of arrays (the M and N sizes are passed as arguments to program, therefore I can't know at compile time).

How do I do this in C++?

I am considering using Vectors, but I'm not sure if it's a good idea since I will have to use the OpenCL library

dominicbri7
  • 2,479
  • 4
  • 23
  • 33

1 Answers1

2

You can pass the array by reference/const reference via a template:

#include <iostream>
#include <cstddef> // for std::size_t

template <typename T, int M, int N, int P>
void f(T (&arr)[M][N][P]) // accepts 3-D arrays of arbitrary types
{
    std::cout << "Size: " << M << " x " << N << " x " << P;
}

int main()
{
    const std::size_t M = 2; 
    const std::size_t N = 3;
    double arr[M][N][4];
    f(arr);
}
vsoftco
  • 55,410
  • 12
  • 139
  • 252
  • for me it would look like `double mat[M][N][2]` where M and N are const size_t but it gives me errors – dominicbri7 Apr 02 '15 at 17:27
  • @dominicbri7 `M` and `N` have to be compile-time constants (not parameters of a function passed via `const`). It should work, see the updated edit. – vsoftco Apr 02 '15 at 17:29
  • That's the thing, as I mentioned in my question the M and N sizes have to be passed as parameters to the program, I have to handle any dimension given (from 3 to 10000) for each dimension – dominicbri7 Apr 02 '15 at 17:35
  • @dominicbri7 sorry, missed that part... Why not then just passing `*arr` for 1-D array, `**arr` for 2-D arrays and so on, together with the dimensions? – vsoftco Apr 02 '15 at 17:36
  • that is what is making me consider using vectors, since they handle their sizes internally and I could even resize them if I needed to, oh well I was looking for a minimal-change solution but I don't think that will happen. – dominicbri7 Apr 02 '15 at 17:44
  • @dominicbri7 yes, if you can use `std::vector`, go straight ahead and use them, try avoiding raw C-style arrays as much as possible. The pointer approach should not be very complicated though, you can still address the elements using array-like indexing, i.e. `arr[2][3][4]` still works whenever you pass `***arr` as your pointer. The problem is that in this case you have to be careful with allocating memory for each slice. Here is a similar question http://stackoverflow.com/questions/15245309/pass-by-reference-multidimensional-array-with-unknown-size – vsoftco Apr 02 '15 at 17:45