Language:c++
System:Linux:
Compile:g++ prog.cpp -o prog
Here is the problem. I have a program that let the user insert the size of two matrices(I'm keeping the matrices 1D instead of 2D as an exercise).The part of the code that is giving me problems is usually fine, except when i put in input:
2
1
1
1
When I do this, the output is segmentation fault between printf("4") and printf("5").
#include <iostream>
int main(void)
{
int oneColoumn, oneRow, twoColoumn, twoRow;
std::cout << "\nHow many coloumns do you want for the first matrix?" << std::endl;
std::cin >> oneColoumn;
std::cout << "\nHow many rows do you want for the first matrix?" << std::endl;
std::cin >> oneRow;
std::cout << "\nHow many coloumns do you want for the second matrix?" << std::endl;
std::cin >> twoColoumn;
std::cout << "\nHow many rows do you want for the second matrix?" << std::endl;
std::cin >> twoRow;
int firstMatrix[oneColoumn*oneRow];
int secondMatrix[twoColoumn*twoRow];
for(int i=0; i < oneColoumn; i++)
{
for(int j=0; j < oneRow; j++)
{
std::cout << "Insert a number for the first matrix";
std::cin >> firstMatrix[i*oneColoumn + j];
}
}
printf("1");
for(int i=0; i < twoColoumn; i++)
{printf("2");
for(int j=0; j < twoRow; j++)
{printf("3");
std::cout << "Insert a number for the second matrix";
printf("4");
std::cin >> secondMatrix[i*twoColoumn + j];
printf("5");
}
}
int threeColoumn, threeRow;
if(oneColoumn>twoColoumn)
threeColoumn=twoColoumn;
if(oneRow>twoRow)
threeRow=twoRow;
int thirdMatrix[threeColoumn*threeRow];
char choice;
std::cout<<"Do you want to add or multiply the two matrices?(a/m)"<<std::endl;
std::cin>>choice;
if(choice=='a')
{
std::cout<<"The two matrices have been added"<<std::endl;
//Addition(firstMatrix,oneRow,oneColoumn,secondMatrix,twoRow,twoColoumn,thirdMatrix,threeRow,threeColoumn);
}
else if(choice=='m')
{
std::cout<<"The two matrices have been multiplied"<<std::endl;
//Multiplication(firstMatrix,oneRow,oneColoumn,secondMatrix,twoRow,twoColoumn,thirdMatrix,threeRow,threeColoumn);
}
}
You have an array indexing issue:
for(int i=0; i < oneColoumn; i++)
{
for(int j=0; j < oneRow; j++)
{
std::cout << "Insert a number for the first matrix";
std::cin >> firstMatrix[i*oneColoumn + j];
}
}
After one completion of the inner loop, you iterate oneRow times.
After two completions of the inner loop, you have iterated 2*oneRow times.
...
etc
You want:
firstMatrix[i*oneRow + j]
Additionally, as others have pointed out, the following two lines declare your arrays on the stack as VLAs (variable length arrays) because the values oneColumn and oneRow are provided by the user and are not known until runtime.
int firstMatrix[oneColoumn*oneRow];
int secondMatrix[twoColoumn*twoRow];
This is not necessarily supported, but may be depending on your compiler. For gcc, see https://gcc.gnu.org/onlinedocs/gcc/Variable-Length.html. And also see this: What's the difference between a VLA and dynamic memory allocation via malloc?
Related
I made an array matrix and used for loops, the problem is that it only displays my last input. Please refer to the sample result below.
#include<iostream>
using namespace std;
int main()
{
int x = 0, y = 0;
int a[x][y], i, j;
cout<<"Enter number of Columns: ";
cin>>y;
cout<<"Enter number of Rows: ";
cin>>x;
cout<<endl;
for(i=0; i<x; i++)
{
cout<<endl;
cout<<"Enter values or row/s: ";
cout<<endl;
for(j=0; j<y; j++)
{
cout<<endl;
cout<<"Row "<< i+1 << ": ";
cin >> a[i][j];
}
}
cout<<endl;
cout<<"Entered Matrix is: ";
cout<<endl;
for(i=0; i<x; i++)
{
for(j=0; j<y; j++)
cout<<a[i][j]<<" ";
cout<<endl;
}
}
SAMPLE RESULT:
Enter number of Columns: 3
Enter number of Rows: 2
Enter values or row/s:
Row 1: -1
Row 1: -2
Row 1: -3
Enter values or row/s:
Row 2: 4
Row 2: 5
Row 2: -6
Entered Matrix is:
4 5 -6
4 5 -6
Just change declaration of array like this:
int[x][y] to int[10][10]
The problem here is that you want to use arrays with a variable size. So, input "x" and "y" and then use this as the array size. (array[x][y])
This does not work in C++. There are no dynamic, so called VLAs (Variable Length Arrays) in C++.
There are some dialects or compiler extensions, which can handle VLA, but C++ does not allow VLAs.
This means, you cannot write somthing like:
int arraySize{};
std::cin >> arraySize;
int array[arraySize];
This is invalid C++ code.
C-Style arrays must have a compile time constant value. You can define it with const or constexpr or even a number literal like 42. Magic constants liek 42 or the worst solution. Anyway, you could write
constepxr int arraySize = 42;
int array[arraySize];
This is syntactically correct.
But, it will not help you. Because you need something "dynamic". The idiomatic correct approach in C++ is to use a std::vector. Please read here about that. And using a 2d std::vector the C++ solution would look like that:
#include <iostream>
#include <vector>
int main() {
// Get user input. Size of matrix. Number of rows and columns
std::cout << "\nEnter number of Rows: ";
if (size_t numberOfRows{}; (std::cin >> numberOfRows) and (numberOfRows > 0)) {
std::cout << "\nEnter number of columns: ";
if (size_t numberOfColumns{}; (std::cin >> numberOfColumns) and (numberOfColumns > 0)) {
// Define 2d matrix and initialze all values to 0
std::vector<std::vector<int>> matrix(numberOfRows, std::vector<int>(numberOfColumns, 0));
// Read all values of matrix
std::cout << "\n\Please enter matrix values in row-column order:\n";
for (std::vector<int>& row : matrix)
for (int& column : row)
std::cin >> column;
// Now show matrix
std::cout << "\n\nThe entered Matrix is:\n\n";
for (std::vector<int>& row : matrix) {
for (int& column : row) std::cout << column << ' ';
std::cout << '\n';
}
}
}
}
But, next, we often hear the statement that you did not learn about std::vector yet. And then, you need to use the approach to use old style memory allocation using new and delete. This is a non-recommend approach, but for teaching purposes, it is still often used.
So, you first allocate memory that will hold pointers to array (for the rows) and then allocate memory for the columns in the rows.
This would then look like the below:
#include <iostream>
int main() {
// Get user input. Size of matrix. Number of rows and columns
std::cout << "\nEnter number of Rows: ";
if (size_t numberOfRows{}; (std::cin >> numberOfRows) and (numberOfRows > 0)) {
std::cout << "\nEnter number of columns: ";
if (size_t numberOfColumns{}; (std::cin >> numberOfColumns) and (numberOfColumns > 0)) {
// Define 2d matrix
int** matrix;
matrix = new int* [numberOfRows];
for (int row = 0; row < numberOfRows; ++row)
matrix[row] = new int[numberOfColumns];
// Read all values of matrix
std::cout << "\n\Please enter matrix values in row-column order:\n";
for (int row = 0; row < numberOfRows; ++row)
for (int column=0; column < numberOfColumns; ++column)
std::cin >> matrix[row][column];
// Now show matrix
std::cout << "\n\nThe entered Matrix is:\n\n";
for (int row = 0; row < numberOfRows; ++row) {
for (int column = 0; column < numberOfColumns; ++column) std::cout << matrix[row][column] << ' ';
std::cout << '\n';
}
// Release memory
for (int row = 0; row < numberOfRows; ++row)
delete [] matrix[row];
delete matrix;
}
}
}
As said, often teached, but strongly discouraged.
Closed. This question needs details or clarity. It is not currently accepting answers.
Want to improve this question? Add details and clarify the problem by editing this post.
Closed 5 years ago.
Improve this question
I want to sum up columns of a predefined 2 D array, but my code seems not to work. E. g. for a 2D array with rows 2 3 and 4 5
I am getting following column sums:
-117393687 and -113194156
Here is the part of my code where I sum up the columns:
//sum columns
for(i=0; i<m; i++)
{
for(ii=0; ii<m; ii++)
{
sum += myarray[i][ii];
}
cout <<"column sum: "<<sum<<endl;
{
Rest of my code:
#include <iostream>
using namespace std;
int main()
{
int i, ii, n, m, sum;
int array[n][m];
sum=0;
cout <"no. of rows"<<endl;
cin>>n;
cout <"no. of columns"<<endl;
cin>>m;
for(i=0; i<n; i++)
{
for(ii=0; ii<n; ii++)
{
cout<<"row "<<i+1<<" column "<<ii+1<<endl;
cin>>array[n][m];
}
}
}
//sum columns
for(i=0; i<m; i++)
{
for(ii=0; ii<m; ii++)
{
sum += myarray[i][ii];
}
cout <<"column sum: "<<sum<<endl;
{
There are quite a few errors on your code, and it has quite a weird structure, but trying not to change it too much (so it's still easy for you to follow the fixes), let's see it fixed then I'll explain it (please note that this version will compile and run in practice):
#include <iostream>
using namespace std;
int main()
{
int i, ii, n, m, sum;
cout << "no. of rows" << endl;
cin >> n;
cout << "no. of columns" << endl;
cin >> m;
int array[n][m];
for (i=0; i<n; i++)
{
for (ii=0; ii<m; ii++)
{
cout << "row " << i+1 << " column " << ii+1 << endl;
cin >> array[i][ii];
}
}
sum=0;
for (i=0; i<n; i++)
{
for (ii=0; ii<m; ii++)
{
sum += array[i][ii];
}
}
cout << "Sum: " << sum << endl;
}
Ok, so, first, you should only declare the array after you know what "n" and "m" variables are. Edit: also, not all compilers will accept declaring the dynamic array that way, but again, I tried to keep your original structure as much as possible.
Second, in your input loop, you should index the array by "i" and "ii", but you were always indexing by "n" and "m", that is, only writing to the latest index, which would even cause an exception.
Last, while summing, again you should use "i" and "ii" as array indices, so you correctly scan the array.
And that is it.
You're not declaring your array size properly. When you create the array n and m aren't set yet. You need to determine their size first. And even then you have to pass in constants to an array because arrays in C++ cannot be dynamically sized. If you want the user to determine container size like this then use a vector of vectors. Arrays are to be used when you know the size from the beginning of the program.
According to the code shown above:
You are mistaking while taking the iputs. Try this:
for(i=0; i<n; i++)
{
for(ii=0; ii<n; ii++)
{
cout<<"row "<<i+1<<" column "<<ii+1<<endl;
cin>>array[i][ii];
}
}
You are initializing the 2D array in a wrong way, you need to define the size first, m and n are not initalized when declaring the array.
On C++ using containers like vector is better.
You also had a error in the input code (2 n instead of n and m in the for loop).
#include <iostream>
#include <vector>
using namespace std;
int main()
{
int rows, cols, sum = 0;
std::vector<std::vector<int>> array;
cout << "No. of rows: ";
cin >> rows;
cout << "No. of columns: ";
cin >> cols;
for(int i = 0; i< rows; i++)
{
std::vector<int> v;
for(int j = 0; j < cols; j++)
{
cout << "Value for row " << i + 1 << " and column "<< j + 1 << ": ";
int val;
cin >> val;
v.push_back(val);
}
array.push_back(v);
}
for (auto i: array)
{
for(auto j: i)
{
sum += j;
}
}
cout << "The sum is: " << sum << endl;
}
I've just completed a program which does as follows:
You have t[10][5] and p[10] arrays.
You read dimT and dimP.
You write dimT values in t[][] and dimP values in p[].
For writing values in t[][], you have to fill lines before. The output must be the column which has highest number of matches for the p[] array.
Example:
INPUT -> 14 (dimT) 2 (dimP) 0 1 2 3 4 0 2 7 9 1 0 11 12 0 (t[][]) 0 0 (p[])
So the final matrix display is:
0 1 2 3 4
0 2 7 9 1
0 11 12 0
OUTPUT -> The best matching column is 0 with 2 matches (overlap counted).
I created this program using arrays but it's really horrible, so I'm looking for a better and cleaner solution from some experts possibly, using vectors instead of simple arrays.
Here is my current code. It would be better if I had split it into a function or two more, but it is shorter this way:
#include <iostream>
#include <vector>
using namespace std;
bool IsMatch(vector<double>& col, vector<double>& p, int n)
{
for (size_t i=0; i<p.size() ;i++)
if (col[i+n]!=p[i])
return false;
return true;
}
int main()
{
int dimT;
int dimP;
cin >> dimT;
cin >> dimP;
int lineN = (dimT+5-1)/5;
vector<vector<double> > t(lineN,vector<double>(5));
vector<vector<double> > tTran(5,vector<double>());
vector<double> p(dimP);
t[lineN-1].resize(dimT%5);
//input matrices
for (int i=0; i<dimT;i++) {
double inputVal;
cin >> inputVal;
tTran[i%5].push_back(inputVal);
t[i/5][i%5]=inputVal;
}
for (int i=0; i<dimP;i++)
cin >> p[i];
//print it out
for (int line=0; line<lineN; line++){
for (size_t j=0; j<t[line].size(); j++)
cout << t[line][j] << " ";
cout << endl;
}
//transpose t
/*vector<vector<double> > tTran(5,vector<double>());
for (int line=0; line<lineN; line++)
for (size_t j=0; j<t[line].size(); j++)
tTran[j].push_back(t[line][j]);
//output tTran
for (int line=0; line<5; line++){
for (size_t j=0; j<tTran[line].size(); j++)
cout << tTran[line][j] << " ";
cout << endl;
}
*/
int maxCol=0;
int maxMatchN=0;
for (int col=0; col<5; col++){
int matchN=0;
for (size_t j=0; j<tTran[col].size()-p.size()+1; j++)
if (IsMatch(tTran[col],p,j) )
matchN++;
if (matchN>maxMatchN){
maxMatchN = matchN;
maxCol = col;
}
}
cout << "The best matching column is " << maxCol
<< " with " << maxMatchN << " matches (overlap counted)." << endl;
}
Here is the simpler (all transposed) version I was suggesting in the comments: The point I'm trying to show is that the non transposed copy has no value. You understood it is easier to transpose during input than later. But you kept the non transposed copy as well, and did the output from the non transposed copy and processing from transposed copy.
Take a look at all the extra nonsense that can be skipped if you don't have a non transposed copy. Then compare the output loop directly from the transposed copy to the original output loop. The change to the output loop was trivial and the benefit significant.
int main()
{
int dimT;
int dimP;
cin >> dimT;
cin >> dimP;
vector<double> t[5+1]; // +1 because empty guard vector makes output loop simpler
vector<double> p(dimP);
//input matrices
for (int i=0; i<dimT;i++) {
double inputVal;
cin >> inputVal;
t[i%5].push_back(inputVal);
}
for (int i=0; i<dimP;i++)
cin >> p[i];
//print it out
for (size_t line=0; line<t[0].size(); line++){
for (size_t j=0; line<t[j].size(); j++)
cout << t[j][line] << " ";
cout << endl;
}
int maxCol=0;
int maxMatchN=0;
for (int col=0; col<5; col++){
int matchN=0;
for (size_t j=0; j<t[col].size()-p.size()+1; j++)
if (IsMatch(t[col],p,j) )
matchN++;
if (matchN>maxMatchN){
maxMatchN = matchN;
maxCol = col;
}
}
cout << "The best matching column is " << maxCol
<< " with " << maxMatchN << " matches (overlap counted)." << endl;
}
That empty "guard" vector is a useful trick to know and in more complicated problems avoids a lot of detail and likely mistakes. In this code it just saved needing j<5 && in one spot.
OK so basically i want this code to get the user to input a value each time into the array and they get to specify the amount of rows and columns. I think i that the problem is that each time the user enters the value it goes into the correct column but also into both rows so by the end it only prints out the last lot of numbers the user had entered in all of the rows.
Sorry if that was hard to understand as this is my first post to this site and as you can probably tell i am only learning c++. So if you could help it would be greatly appreciated.
#include <iostream>
using namespace std;
int main()
{
int row;
int column;
int value[row][column];
cout << "How Many Rows?\n";
cin >> row;
cout << "How Many Columns\n";
cin >> column;
for(int x = 0; x<row; x++) {
for(int y = 0; y<column; y++) {
cout << "Enter Value Now\n";
cin >> value[x][y];
}
cout << endl;
}
cout << endl;
for(int a = 0; a < row; a++) {
for(int b = 0; b < column; b++) {
cout << value[a][b] << " ";
}
cout << endl;
}
}
int value[row][column];
declares an array whose dimensions are based on 2 uninitialised values.
If you don't have to use a C-style array, you could use
std::vector<std::vector<int>> value;
and choose its dimensions based on user input.
Alternatively, you could continue to use a C-style array if you allocate it like
int** value;
// input row/column
value = new int*[row];
for (int i=0; i<row; i++) {
value[i] = new int[column];
}
If you use the latter approach, make sure to also delete all dynamically allocated memory later.
I'm trying to just make a simple program where the user inputs every value of a matrix, then the program prints the matrix. So far I have
#include <iostream>
using namespace std;
int main()
{
int n;
cout << "A is an nxn matrix.\nn=";
cin >> n;
int matrix[n-1][n-1];
for (int i=0;i<n;i++)
{
for (int j=0;j<n;j++)
{
cout << "A[" << i+1 << "][" << j+1 << "]=";
cin >> matrix[i][j];
}
}
cout << "[[ ";
for (int i=0;i<n;i++)
{
for (int j=0;j<n;j++)
{
cout << matrix[i][j] << " ";
}
if (i!=n-1) //Just to make the output pretty
cout << "]\n [ ";
else
cout << "]]";
}
}
`
However, whenever I put in a matrix of any size, for instance [[1,2,3][4,5,6][7,8,9]], the program returns [[1,2,4][4,5,7][7,8,9]].
Can anyone tell me why this is happening and how to fix it?
You're getting an undefined behavior for accessing out of range in matrix[i][j] when i or j equals n-1 for your matrix declared as matrix[n-1][n-1]
Use:
int matrix[n][n]; // will say 0 to n-1
instead of
int matrix[n-1][n-1];
Should be int matrix[n][n]. Generally, an array A[n] has indexes from 0 to n-1.
You are overflowing the boundaries of the row, for example, if you have int matrix[2][2] and set matrix[0][2] = 42, you are actually assigning matrix[1][0], and when you set matrix[2][0] you are writing beyond the array boundaries potentially destroying some other variables or even call stack, which may cause undefined behavior.