Jame
Jame

Reputation: 3854

Which way is faster to copy the data from a matrix to other matrix in C/C++?

I have two matrix which are A1 and A. The matrix A1 has data. I want to copy (two cases):

  1. All data from A1 to A
  2. Copy selected row from A1 to A

I have two way to copy A1 to A for each case. It is that I will copy each element from A1 to A. Or, I will copy by using memcpy. Which way is more faster in C/C++. Could you see the way which uses memcpy and let me know if it was wrong? Thanks

***********************************************************************************/
    typedef unsigned char  U8;
    typedef unsigned int   U32;
    U8** A1;
    U8** A;
    //Alloc A1 and A matries
    int M1=32;
    int N1=64;
    int M=64;
    int N=128;
    A1= new U8*[M1]; //Max number of rows that M can achieve 
    for (U32 i = 0; i < N1; ++i)
    {
      A1[i] = new U8[N1];
      memset(A1[i],0,N1);
    }
    A= new U8*[M]; //Max number of rows that M can achieve 
    for (U32 i = 0; i < N; ++i)
    {
      A[i] = new U8[N];
      memset(A[i],0,N);
    }

    // Assume A1 is set data in here
    // Now we will copy A1 to A
    // Use first way- copy element by element
    for (U32 i = 0; i < M; ++i)
    {
      for(U32 j=0; j<N;j++)
          A[i] = A1[i];
    }
    //Use second way is memset
    for (U32 i = 0; i < M; ++i)
    {
         memcpy(A[i],A1[i],N);
    }

Upvotes: 1

Views: 242

Answers (2)

Semyon Burov
Semyon Burov

Reputation: 1172

First: memset's third argument is number of bytes, that should be set by value of second argument. Use NumberOfElements * sizeof(TypeOfElements):

for (U32 i = 0; i < N1; ++i)
{
  A1[i] = new U8[N1];
  memset(A1[i],0,N1 * sizeof(U8));
}
A= new U8*[M]; //Max number of rows that M can achieve 
for (U32 i = 0; i < N; ++i)
{
  A[i] = new U8[N];
  memset(A[i],0,N * sizeof(U8));
}

Second: you con't run your loops to M and N because in A1 memory was allocated only to M1 and N1 which is less than M and N in current context. Also you forgot second index then you matrix copying by elements.

for (U32 i = 0; i < M1; ++i)
{
  for(U32 j=0; j<N1;j++)
      A[i][j] = A1[i][j];
}
//Use second way is memset
for (U32 i = 0; i < M1; ++i)
{
     memcpy(A[i],A1[i],N1 * sizeof(U8));
}

P.S. Don't forget about free memory after you allocate it. Add somthing like

void destroy(U8 **matrix, int rowCount) {
    for (int i = 0; i < rowCount; i++) {
        delete [] matrix[i];
    }
    delete []matrix;
}

and call this function after all work with matrix was down.

Edit: In loops which copying values via memcpy I change indices from M and N to M1 and N1. Previous where incorrect.

Upvotes: 3

Rabbid76
Rabbid76

Reputation: 210978

You can allocate and copy the memory for the matrix data at once:

U8** A;
A = new U8*[M];      // allocate memory for pointer to rows
A[0] = new U8 [M*N]; // allocate memory for matrix data
for (int i = 1; i < M; i++)
    A[i] = A[i-1]+N    // assigne to each row its memory
memset(A[0], 0, M*N*sizeof(U8));

// copy matrix data
memcopy(A1[0], A[0], M*N*sizeof(U8));  

Upvotes: 1

Related Questions