Arrays and pow

I need your help. How can I write a matrix(3*3) with random numbers. And then, ask the user to type N to pow and show the results of the pow of that array.
Last edited on
if you want the power of a matrix, you need to write it, or use a library. C++ does not have built in matrix tools. https://www.algebrapracticeproblems.com/power-of-a-matrix/ has an explain of it, and its best if you have access to the eigenvalues, which starts to get hairy to do on your own.

pow works on one item, like pi cubed.

<random> is your header for random numbers.
https://www.cplusplus.com/reference/random/ is the starting page but
https://www.cplusplus.com/reference/random/uniform_int_distribution/ has a great simple example.

std::valarray may be useful here - as it an overload for pow()

http://www.cplusplus.com/reference/valarray/
The valarray operations are elemental operations - they raise each element of the array independently to a power, not do what (I assume) is intended: repeatedly doing a matrix multiply.

If you aren't using a separate library then you would still (in c++) have to code for yourself a matmul() operation.

I have a nasty suspicion that the poster here may be about to launch spam, but let's see if he comes up with an attempt at code ...
So far this is what I got:

#include <stdio.h>
#include <stdlib.h>
#include <conio.h>

int main()
{
int m, n, p, q, c, d, k, sum = 0;
int first[3][3], power[3][3];

printf("Ingrese el numero de columnas y filas\n");
scanf("%d%d", &m, &n);

for (c=0;c<=m-1;c++){
for (d=0;d<=n-1; d++){
first[c][d]=rand () % 9;

}
}

printf(" \n");
for(c=0;c<=m-1;c++){
for (d=0;d<=n-1; d++){
printf("%d ",first[c][d]);
}
printf("\n");
}


}


Still learning how to use getch and return but I can't find a way to pow the result
Write a routine to multiply two matrices. The power can be found by repeat multiply; e.g.
A4 = A * A * A * A



First, these achieve the same:
1
2
for (c=0; c<=m-1; c++)
for (c=0; c<m; c++)

The latter is how C/C++ for loops are usually written.

Second: names. Descriptive names are not much more to write, but with them one can avoid some logical mistakes. For example:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
int rows, cols, row, col;
int first[3][3]
int power[3][3];

printf("Ingrese el numero de columnas y filas\n");
scanf("%d%d", &rows, &cols);

for (row=0; row<rows; row++){
  for (col=0; col<cols; col++){
    first[row][col]=rand () % 9;
  }
}

printf(" \n");
for (row=0; row<rows; row++){
  for (col=0; col<cols; col++){
    printf("%d ", first[row][col]);
  }
  printf("\n");
}

Note that multi-dimensional arrays have row-major layout in C.

"Array" in C means 1D array. You have 2D array that could be called "matrix".

You have reserved memory for 3*3 matrices. Then you ask from user the number of rows and columns. What if the user types '7' and '42'? Your code would try to fill a 7*42 matrix 294 integers, but the first has room for only 9 integers!

Besides, you wrote:
write an array (3*3) with random numbers. And then, ask the user to type N to pow

That does not say "m rows and n columns". It says 3 rows and 3 columns.
What is N? Is it how many times you should multiply the matrix with itself? One number.

Last, if rows != columns, then you can't multiply matrix with itself.


PS. Posting code in code tags makes it easier to read. See https://www.cplusplus.com/articles/jEywvCM9/
Last edited on
Looks about right but still needs to be thoroughly checked:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
#include <iostream>
#include <ctime>

void populate(int array[][3])
{
    for(int i = 0; i < 3; i++)
    {
        for(int j = 0; j < 3; j++)
        {
            array[i][j] = i-j; // rand() % 2; // <-- VALUE GENERATOR FUNCTION
        }
    }
}

void display(int array[][3])
{
    for(int i = 0; i < 3; i++)
    {
        for(int j = 0; j < 3; j++)
        {
            std::cout << array[i][j] << ' ';
        }
        std::cout << '\n';
    }
    std::cout << '\n';
}

void multiply(int x[][3], int y[][3], int z[][3])
{
    for (int i = 0; i < 3; i++)
    {
        for (int j = 0; j < 3; j++)
        {
            z[i][j] = 0;
            
            for (int k = 0; k < 3; k++) {
                z[i][j] += x[i][k] * y[k][j];
            }
        }
    }
}


int main()
{
    int A[3][3]{0};
    int product[3][3]{0};
    
    populate(A);
    display(A);
    
    // N = 2
    multiply(A, A, product);
    display(product);
    
    // N > 2
    for(int i = 0; i < 10; i++)
    {
        multiply(product, A, product);
        display(product);
    }
    
    return 0;
}



0 -1 -2 
1 0 -1 
2 1 0 

-5 -2 1 
-2 -2 -2 
1 -2 -5 

0 1 -1 
-6 4 8 
-12 7 17 

-1 0 2 
20 -12 -28 
41 -24 -58 

4 -2 -6 
-68 40 96 
-140 82 198 

-14 8 20 
232 -136 -328 
478 -280 -676 

48 -28 -68 
-792 464 1120 
-1632 956 2308 

-164 96 232 
2704 -1584 -3824 
5572 -3264 -7880 

560 -328 -792 
-9232 5408 13056 
-19024 11144 26904 

-1912 1120 2704 
31520 -18464 -44576 
64952 -38048 -91856 

6528 -3824 -9232 
-107616 63040 152192 
-221760 129904 313616 

-22288 13056 31520 
367424 -215232 -519616 
757136 -443520 -1070752 

Program ended with exit code: 0
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
#include <iostream>
#include <iomanip>
#include <vector>
#include <random>
#include <cassert>
#include <cmath>
#include <ctime>
using namespace std;

using vec = vector<double>;
using matrix = vector<vec>;

//==========================================================

mt19937 gen( time(0) );
uniform_real_distribution<double> uni( 0.0, 1.0 );
double RNG( double a, double b ){ return a + ( b - a ) * uni( gen ); }

//==========================================================

ostream & operator << ( ostream &out, const matrix &M )
{
   for ( auto &row : M )
   {
      for ( auto e : row ) out << setw( 15 ) << e << " ";
      out << '\n';
   }
   return out;
}

//==========================================================

matrix operator *( const matrix& A, const matrix &B )
{
   assert( A[0].size() == B.size() );            // check for compatibility

   matrix M( A.size(), vec( B[0].size(), 0.0 ) );
   for ( int i = 0; i < A.size(); i++ )
   {
      for ( int j = 0; j < B[0].size(); j++ )
      {
         for ( int k = 0; k < A[0].size(); k++ ) M[i][j] += A[i][k] * B[k][j];
      }
   }
   return M;
}

//==========================================================

matrix identity( unsigned n )
{
   matrix M( n, vec( n, 0.0 ) );
   for ( int i = 0; i < n; i++ ) M[i][i] = 1;
   return M;
}

//==========================================================

matrix randMatrix( unsigned n, double a, double b )
{
   matrix M( n, vec( n ) );
   for ( auto &row : M )
      for ( auto &e : row ) e = RNG( a, b );
   return M;
}

//==========================================================

matrix pow( const matrix& A, unsigned n )        // cheap and cheerful by repeated multiply (quicker by powers of 2)
{
   assert( A.size() == A[0].size() );            // check square matrix

   if ( n == 0 ) return identity( A.size() );
   if ( n == 1 ) return A;
   return A * pow( A, n - 1 );
}

//==========================================================

int main()
{
   matrix M = randMatrix( 3, -10.0, 10.0 );
   cout << "M=\n" << M << "\n\n";

   for ( unsigned i = 0; i < 5; i++ ) cout << "pow(M," << i << ") = \n" << pow( M, i ) << "\n\n";
}



M=
       -4.44505      -0.0967078        -3.07706 
       -7.94277         8.10793         -3.2705 
        -9.4166        -2.35602         2.80122 


pow(M,0) = 
              1               0               0 
              0               1               0 
              0               0               1 


pow(M,1) = 
       -4.44505      -0.0967078        -3.07706 
       -7.94277         8.10793         -3.2705 
        -9.4166        -2.35602         2.80122 


pow(M,2) = 
         49.502         6.89539         5.37443 
         1.7035         74.2121         -11.238 
        34.1926        -24.7915         44.5276 


pow(M,3) = 
       -325.416         38.4578        -159.817 
       -491.198         628.018        -279.432 
       -374.373        -309.223           100.6 


pow(M,4) = 
        2645.96         719.816         427.866 
       -173.508         5797.78        -1325.24 
        3172.88        -2707.97         2445.08 



A matrix A to the zeroth(?) power A0 is by definition the identity matrix I.
Last edited on
Thank you for your help. I managed to create the code and the power by multiplying the matrix but can't find a way to automatically generate the numbers in the matrix. This is what I wrote:

#include <stdio.h>
#include <conio.h>
#include <stdlib.h>

int main(){
int n, p;
int m[3][3];
int r[3][3];
int t[3][3];


printf("Number for matrix: ");
if (scanf("%d", &n) != 1 || n <= 0)
return 1;
printf("To the power of: ");
if (scanf("%d", &p) != 1 || p <= 0)
return 1;

printf("Elements of Matrix\n");



for (int b = 0; b < n; b++) {
for (int d = 0; d < n; d++) {
printf("[%d][%d] = ", b + 1, d + 1);
if (scanf("%d", &m[b][d]) != 1)
return 1;
r[b][d] = b == d;
}
}

for (int i = 0; i < p; i++) {
for (int b = 0; b < n; b++) {
for (int d = 0; d < n; d++) {
int sum = 0;
for (int k = 0; k < n; k++) {
sum += r[b][k] * m[k][d];
}
t[b][d] = sum;
}
}
for (int b = 0; b < n; b++) {
for (int d = 0; d < n; d++) {
r[b][d] = t[b][d];
}
}
}

printf("Result:\n");
for (int c = 0; c < n; c++) {
for (int d = 0; d < n; d++) {
printf("%3d ", r[c][d]);
}
printf("\n");
}
getch ();
return 0;
}


If you notice, it's asking the user to manually enter the numbers. I think I'm almost there but don't know exactly where to put "rand()". I've tried everything I can imagine but nothing comes up automatically.


I want to keep it simple by using just positive numbers.
Last edited on
In the first code that you did post you did use rand(). Surely you know what you did there?
not sure what this is for, but if you want large powers using simple approaches, just like with numbers, you can factor around it.
that is
x to the 10th power is just
y = x*x; //squared
z = y*y; //4th power
q = z*z; //8th power...
R = q*y //10th power
which would save a lot of redundant multiplies. 4 instead of 10, and the bigger the power, the more you save. If you look closely, the bits of the power are tied to the multiplications.
Last edited on
Topic archived. No new replies allowed.