Matrix vector product

Hi, i have an assigment where i am requirede to compute the matrix-vector product.
When I try to run the program, I get an error message saying "Program file does not exist".
I'm pretty sure I have some errors in the bottom "void multiplik".


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
87
88
89
90
91
92
93
94
95
96
  #include <iostream>
#include <fstream>
#include <cmath>
using namespace std;
#define nmax 50

void indhent_vektor(string fn, double v[nmax], int &n);
void udskriv_vektor(double v[nmax], int &n);

void indhent_matrix(string fn, double A[nmax][nmax],int &n, int &m);
void udskriv_matrix(double v[nmax][nmax], int &n, int m);

void multiplik(double A[nmax][nmax], double v[nmax], int &n);


int main() {

	double v[nmax],A[nmax][nmax];
	int n, n1, m1;


indhent_vektor("vektor.txt", v, n);
cout<<"\nIndhent vektor fra fil";
udskriv_vektor(v,n);

indhent_matrix("matrix.txt",A,n1,m1);
cout << "\nIndhent matrix fra fil";
udskriv_matrix(A,n1,m1);

multiplik(A,v,n);

	return 0;
}

void indhent_vektor(string fn, double v[nmax], int &n){
	ifstream fil;
	fil.open(fn);
	fil >> n;

	for (int i=0;i<n;i++){
		fil>>v[i];
		}
	fil.close();
}


void udskriv_vektor(double v[nmax], int &n){
	for (int i=0;i<n;i++){
		cout<<"\n["<<v[i]<<"]";
		}

}



void indhent_matrix(string fn, double A[nmax][nmax],int &n, int &m){
	ifstream fil;
	fil.open(fn);
	fil>>n;
	fil>>m;

	for (int i=0;i<n;i++){
		for (int j=0;j<m;j++){
		fil>>A[i][j];
		}
	}
	fil.close();
}


void udskriv_matrix(double v[nmax][nmax], int n, int m){
	for (int i=0;i<n;i++){
		cout<<"\n["<<v[i][0];
		for (int j=1;j<n;j++){
			cout<<" "<<v[i][j];

		}
cout << "]";
	}

}

void multiplik(double A[nmax][nmax], double v[nmax], int &n){
double p[nmax];
	for (int i=0; i<n; i++){
		p[i]=0;
		//multiplikation.
		for(int i=0; i<n; i++){
			for(int j=0;j<n;j++){
				p[i]+=A[i][j]*v[i];
			}
		}

		}
	}
Hello mikkeldl,

Thank you for using code tags.

The only thing missing from your OP, (Original Post), is the input file. Do not make people guess at what the file should be. There is a good chance it will be different from yours. If it is a large file a a goo sample will do, say maybe 10 records or 5, also include any part of the file that may be giving you a problem.

It is hard to test your program with out a proper input file, but I do not believe that problem is in the "multiplik" function, but may start in the "indhent_matrix" function.

In the "indhent_matrix" function you define a file stream "fil". FWIW I kike using the name "inFile", It makes the code easier to follow. And for "fn" call it "fileName". There is no guess work and you breeze right through the code with out stumbling trying to remember what "fil" or "fn" means.

The more important part here is that you have defined a file stream variable and used the "open" function to open the file, but how do you know it is open and ready to use?

The file may not be open or usable, but the program continues as if nothing is wrong until the for loop can nor read anything from the file which makes the "multiplik" function look like it is the problem when it is not.

Once I get your code set up and changed I will show you what I mean. Hopefully I will have an input file to work with by then.

Andy
Last edited on
Hi H. Andy,

The input files are 2 text documents containing the following

vektor.txt:

4

1
2
3
4


matrix.txt:
4
4

1 2 3 4
2 3 4 5
3 4 5 6
6 7 8 9
mikkeldl wrote:
I'm pretty sure I have some errors in the bottom "void multiplik".


Yes, you do.

Firstly, you aren't either printing out or, better, returning the answer p[].

Secondly, you are trying to nest TWO i loops - the second isn't needed.

Thirdly, your matrix-vector multiplication is wrong;
p[i]+=A[i][j]*v[i];
should be
p[i]+=A[i][j]*v[j]; // final i should be j
Hello mikkeldl,

Thank you for the input files.

This is what I am thing of:
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
int indhent_matrix(string fileName, double A[nmax][nmax], int &n, int &m)
{
    ifstream inFile;
    inFile.open(fileName);
    //ifstream inFile(fileName);  // <--- The above lines can be shortened to this. And this is what is most often used.

    if (!inFile)
    {
        //std::cout << "\n File " << std::quoted(inFileName) << " did not open." << std::endl;
        std::cout << "\n File \"" << fileName << "\" did not open." << std::endl;

        return 1;
    }

    inFile >> n;
    inFile >> m;

    for (int i = 0; i < n; i++)
    {
        for (int j = 0; j < m; j++)
        {
            inFile >> A[i][j];
        }
    }

    return 0;  // <--- Means every thing is good.

    //fil.close();  // <--- Not required as the dtor will close the file when the function looses scope.
}


Then when calling the function in "main":
1
2
3
4
if (response = indhent_matrix("matrix.txt", A, n1, m1))
{
    return response;
}

"response" is defined as an "int".

Some other things I noticed:
You need to include the header file "<string>". Just because your IDE may not have a problem with defining "string someVar" You may find other problems when trying to use "someVar" without the "<string>" header file.

For the moment I have found no code that would require "<cmath>". This is not needed for simple things like "+, -, *, / and %". These are built into the IDE/compiler.

When I did test the files I received this output on the screen:

Indhent vektor fra fil
[1]
[2]
[3]
[4]
Indhent matrix fra fil
[1 2 3 4]
[2 3 4 5]
[3 4 5 6]
[6 7 8 9]


At least I know some of the program works.

I also noticed, because it was flagged as an error:
The prototype void udskriv_matrix(double v[nmax][nmax], int &n, int m); does not match the function definition of void udskriv_matrix(double v[nmax][nmax], int n, int m)

Also "n" and "m" are cute variable names, but have no meaning. Try to avoid single letter variable names in favor of something that better describes what the variable is or used for. In this case I believe that "rows" is better than "n" and "cols" for "m". This will make the code easier to follow with less confusion.

Then for the for loops:
1
2
3
4
5
6
7
for (int row = 0; row < rows; row++)
{
    for (int col = 0; col < cols; col++)
    {
        inFile >> A[row][col];
    }
}

As you can see there is much less confusion this way.

Andy
Last edited on
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
87
88
89
90
91
92
93
94
95
96
97
98
#include <iostream>
#include <fstream>
using namespace std;

const size_t nmax {50};

void indhent_vektor(const string& fn, double v[nmax], size_t& n);
void udskriv_vektor(double v[nmax], size_t n);

void indhent_matrix(const string& fn, double A[nmax][nmax], size_t& n, size_t& m);
void udskriv_matrix(double v[nmax][nmax], size_t n, size_t m);

void multiplik(double A[nmax][nmax], double v[nmax], size_t n);

int main()
{
	double v[nmax] {}, A[nmax][nmax] {};
	size_t n {}, n1 {}, m1 {};

	indhent_vektor("vektor.txt", v, n);
	cout << "\nIndhent vektor fra fil";
	udskriv_vektor(v, n);

	indhent_matrix("matrix.txt", A, n1, m1);
	cout << "\nIndhent matrix fra fil";
	udskriv_matrix(A, n1, m1);

	cout << "\nMultiplied";
	multiplik(A, v, n);

	return 0;
}

void indhent_vektor(const string& fn, double v[nmax], size_t& n)
{
	ifstream fil(fn);

	if (fil) {

		fil >> n;

		for (size_t i = 0; i < nmax && i < n && fil >> v[i]; ++i);

		fil.close();
	} else
		cout << "Cannot open file " << fn << '\n';
}

void udskriv_vektor(double v[nmax], size_t n) {
	for (size_t i = 0; i < n; ++i)
		cout << "\n[" << v[i] << "]";

	cout << '\n';
}

void indhent_matrix(const string& fn, double A[nmax][nmax], size_t& n, size_t& m) {
	ifstream fil(fn);

	if (fil) {
		fil >> n;
		fil >> m;

		for (size_t i = 0; i < nmax && i < n; ++i)
			for (size_t j = 0; j < nmax && j < m; ++j)
				fil >> A[i][j];

		fil.close();
	} else
		cout << "Cannot open file " << fn << '\n';
}

void udskriv_matrix(double v[nmax][nmax], size_t n, size_t m) {
	for (size_t i = 0; i < n; ++i) {
		cout << "\n[" << v[i][0];

		for (size_t j = 1; j < m; ++j)
			cout << ' ' << v[i][j];

		cout << ']';
	}

	cout << '\n';
}

void multiplik(double A[nmax][nmax], double v[nmax], size_t n) {
	double p[nmax] {};

	for (int i = 0; i < n; i++)
		for (int j = 0; j < n; j++)
			p[i] += A[i][j] * v[j];

	cout << "\n[" << p[0];

	for (size_t k = 1; k < n; ++k)
		cout << ' '<< p[k];

	cout << "]\n";
}



Indhent vektor fra fil
[1]
[2]
[3]
[4]

Indhent matrix fra fil
[1 2 3 4]
[2 3 4 5]
[3 4 5 6]
[6 7 8 9]

Multiplied
[30 40 50 80]

Topic archived. No new replies allowed.