Home > Software engineering >  Initialize a const array with random numbers
Initialize a const array with random numbers

Time:06-09

I have been tasked to calculate the time it takes for my PC to do a matrix multiplication with dimensions 2048x2048 (and get 10 samples) and I was given the following function

/*
 * matrixMult - Matrix multiplication
 */
void matrixMult(float *const C, /* output matrix */
float const *const A, /* first matrix */
float const *const B, /* second matrix */
int const n) { /* number of rows/cols */
  for (int i = 0; i < n; i  ) { /* rows */
    for (int j = 0; j < n; j  ) { /* cols */
      /* initialize output value */
      C[sub2ind(i, j, n)] = 0;
      for (int k = 0; k < n; k  ) { /* accumulate products */
        C[sub2ind(i, j, n)]  = A[sub2ind(i, k, n)] * B[sub2ind(k, j, n)];
      }
    }
  }
} // end function 'matrixMult'

and this to use in my main

double time = 0.0;
/* compute matrix multiplication */
for (int it = 0; it < MAX_ITER; it  ) {
  gettimeofday(&start, NULL);
  matrixMult( C, A, B, n );
  gettimeofday(&end, NULL);
  time = ( (end.tv_sec - start.tv_sec) * 1000.0   /* sec to ms */
      (end.tv_usec - start.tv_usec) / 1000.0 ); /* us to ms */
  fprintf("Iter: %d Time: %f\n", it, time);
}

So what I have to do is initialize the arrays A and B with random values?
I can't think of a way.
This is what I have so far

#include <stdio.h>
#include <time.h>
#include <math.h>
#include <stdlib.h>
#define sub2ind(i,j,n) (j)  (i)*(n)
float *const A, *const B, *const C;

void matrixMult(float *const C, /* output matrix */
float const *const A, /* first matrix */
float const *const B, /* second matrix */
int const n);

int main() {
  int n = 2048;
  double time = 0.0;
  struct timeval start, end;
  /* compute matrix multiplication */
  for (int it = 0; it < 10; it  ) {
    gettimeofday(&start, NULL);
    matrixMult(C, A, B, n);
    gettimeofday(&end, NULL);
    time = ((end.tv_sec - start.tv_sec) * 1000.0   /* sec to ms */
    (end.tv_usec - start.tv_usec) / 1000.0); /* us to ms */
    fprintf("Iter: %d Time: %f\n", it   1, time);
  }
  return 0;
}

/*
 * matrixMult - Matrix multiplication
 */
void matrixMult(float *const C, /* output matrix */
    float const *const A, /* first matrix */
    float const *const B, /* second matrix */
    int const n) { /* number of rows/cols */
  for (int i = 0; i < n; i  ) { /* rows */
    for (int j = 0; j < n; j  ) { /* cols */
      /* initialize output value */
      C[sub2ind(i, j, n)] = 0;
      for (int k = 0; k < n; k  ) { /* accumulate products */
        C[sub2ind(i, j, n)]  = A[sub2ind(i, k, n)] * B[sub2ind(k, j, n)];
      }
    }
  }
} // end function 'matrixMult'

CodePudding user response:

float *const A, *const B, *const C; are global pointers. Each, at program start, are given a value 0, a null pointer. Since they are const, the pointer cannot change. We are stuck.


Instead, do not make them const - there is no need for that. In main(), allocate memory and values before the test.

Note that matrixMult() uses a pointer to float rather than a more 2D like type. We can take advantage of that when first assigning A, B.

float *A, *B, *C;

int main() {
   ...
   A = malloc(sizeof A[0] * n * n);
   B = malloc(sizeof B[0] * n * n);

   // Zero fill product array in case multiplication is in error.
   // Assigning simplifies debugging.
   C = calloc((size_t)n * n, sizeof C[0]);  

   // If out-of-memory ...
   if (A == NULL || B == NULL || C == NULL) {
     // Might as well exit code here with an error message
   }

   // Fill A[], B[] with something interesting.
   for (size_t i = 0; i < (size_t)n * n; i)) {
     A[i] = rand();
     B[i] = rand();
   }
   
   // Test code here.
  ... 

   // Clean up
   free(A); A = NULL;
   free(B); B = NULL;
   free(C); C = NULL;
}

Notes: #define sub2ind(i,j,n) (j) (i)*(n) risks precedence issues. Better as #define sub2ind(i,j,n) ((j) (i)*(n)). Even better as #define sub2ind(i,j,n) (j) (size_t)(i)*(n) to insure size_t math as int math is more likely will to overflow.

CodePudding user response:

I would reccoment for you to check out the standard function rand()

int rand( void )

It returns with a random intiger between 0 to RAND_MAX.

  • Related