How I can sort two dimensional array's columns? - c++

Helle everyone I want sort two dimensional array's columns.I want to take the dimensions and elements of the array from the user and display it as a matrix. Then subtract the sorted form of the same array. We just need to sort the columns of the array. Please help.
Something like that
{{0, 1, 3},
{6, 0, 8},
{5, 9, 2}}
{{0, 0, 2},
{5, 1, 3},
{6, 9, 8}}
I wrote code in C ++ for this, I can just sort the first column of the array and display it, but I can't do the other columns. I appeal to you for this.
#include <iostream>
using namespace std;
int main()
{
int column, row;
cout << "Column = ";
cin >> column;
cout << "Row = ";
cin >> row;
int array[column][row];
int sortedarray[column];
for (int z = 0; z < column; z++) {
for (int a = 0; a < row; a++) {
cin >> array[z][a];
}
}
for (int i = 0; i < column; i++) {
sortedarray[i] = array[i][0];
}
cout << "\n";
for (int y = 0; y < column; y++) {
for (int i = 0; i < row; i++) {
cout << array[y][i] << " ";
}
cout << endl;
}
cout << "\n";
int temp = 0;
for (int i = 1; i < column; i++)
for (int j = 0; j < column - i; j++) {
if (sortedarray[j] > sortedarray[j + 1]) {
temp = sortedarray[j];
sortedarray[j] = sortedarray[j + 1];
sortedarray[j + 1] = temp;
}
}
cout << "COUT sorted array \n ";
for (int i = 0; i < column; i++) {
cout << sortedarray[i] << " ";
}
}

Here is my solution:
#include <iostream>
#include <iomanip>
#include <vector>
#include <tuple>
int getDigitCount( int num )
{
num = abs( num );
return ( num < 10 ? 1 :
( num < 100 ? 2 :
( num < 1000 ? 3 :
( num < 10'000 ? 4 :
( num < 100'000 ? 5 :
( num < 1'000'000 ? 6 :
( num < 10'000'000 ? 7 :
( num < 100'000'000 ? 8 :
( num < 1'000'000'000 ? 9 :
10 )))))))));
}
void printMatrix( const std::vector<int>& array,
const std::tuple< const size_t, const size_t >& dimensions, const int maxDigitCount )
{
const auto& [ rowCount, colCount ] { dimensions };
std::cout << '\n' << " \\ Column ";
for ( size_t colNumber = 0; colNumber < colCount; ++colNumber )
{
std::cout << std::left << std::setw( maxDigitCount + 2 ) << std::setfill(' ') << colNumber;
}
std::cout << '\n' << "Row \\" << '\n' << '\n';
for ( size_t idx = 0; idx < rowCount * colCount; ++idx )
{
if ( ( idx ) % ( colCount ) == 0 )
{
std::cout << " " << ( idx ) / ( colCount ) << " ";
}
std::cout << std::left << std::setw( maxDigitCount + 2 ) << std::setfill(' ') << array[ idx ];
if ( ( idx + 1 ) % ( colCount ) == 0 )
{
std::cout << '\n' << '\n';
}
}
}
// get row count and column count from the user
auto getDimensions( )
{
constexpr int MIN_ALLOWED_ROW_COUNT { 1 };
constexpr int MIN_ALLOWED_COL_COUNT { 1 };
constexpr int MAX_ALLOWED_ROW_COUNT { 50 };
constexpr int MAX_ALLOWED_COL_COUNT { 50 };
int inputRowCount { };
int inputColCount { };
do
{
std::cout << "Enter row count: ";
std::cin >> inputRowCount;
std::cout << "Enter column count: ";
std::cin >> inputColCount;
} while ( inputRowCount < MIN_ALLOWED_ROW_COUNT || inputColCount < MIN_ALLOWED_COL_COUNT ||
inputRowCount > MAX_ALLOWED_ROW_COUNT || inputColCount > MAX_ALLOWED_COL_COUNT );
return std::make_tuple<int, int>( std::move( inputRowCount ), std::move( inputColCount ) );
}
// get user input ( user's matrix ) and populate the array
void getArrayElements( std::vector<int>& array, int& maxDigitCount )
{
for ( std::vector<int>::iterator it = array.begin( ); it != array.end( ); ++it )
{
std::cin >> *it;
if ( getDigitCount( *it ) > maxDigitCount )
{
maxDigitCount = getDigitCount( *it );
}
}
}
// bubble sort the array
void bubbleSortArray( std::vector<int>& array, const size_t& elementCount )
{
for ( size_t iterCount = 0; iterCount < elementCount - 1; ++iterCount )
{
for ( size_t idx = 0; idx < ( elementCount - 1 - iterCount ); ++idx )
{
if ( array[ idx ] > array[ idx + 1 ] )
{
int temp = array[ idx ];
array[ idx ] = array[ idx + 1 ];
array[ idx + 1 ] = temp;
}
}
}
}
// transpose 1D array and store in 1D transposedArray
void transposeMatrix( std::vector<int>& array, std::vector<int>& transposedArray,
const std::tuple< const size_t, const size_t >& dimensions )
{
size_t row { };
size_t col { };
const auto& [ rowCount, colCount ] { dimensions };
for ( size_t idx = 0; idx < rowCount * colCount; ++idx )
{
if ( col == colCount )
{
++row;
col = 0;
}
size_t newIdx { row + ( col * rowCount ) };
transposedArray[ newIdx ] = array[ idx ];
++col;
}
}
void launch( )
{
const auto [ inputRowCount, inputColCount ] = getDimensions( );
const size_t rowCount { static_cast<unsigned int>( inputRowCount ) };
const size_t colCount { static_cast<unsigned int>( inputColCount ) };
const std::tuple< const size_t, const size_t > dimensions( std::move( rowCount ),
std::move( colCount ) );
const size_t elementCount { rowCount * colCount };
std::vector<int> array( elementCount ); // the 1D array for storing the user's matrix
int maxDigitCount { };
getArrayElements( array, maxDigitCount );
std::cout << "\nOriginal 2D array:\n"; // print out the array
printMatrix( array, dimensions, maxDigitCount );
bubbleSortArray( array, elementCount );
std::cout << "\nSorted 2D array:\n"; // print out the sorted array
printMatrix( array, dimensions, maxDigitCount );
std::vector<int> transposedArray( elementCount );
transposeMatrix( array, transposedArray, dimensions );
std::cout << "\nTransposed sorted 2D array:\n"; // print out the transposed sorted array
printMatrix( transposedArray, std::make_tuple< const size_t, const size_t >
( std::move( colCount ), std::move( rowCount ) ), maxDigitCount );
}
int main()
{
launch( );
return 0;
}
And a sample input/output:
Enter row count: 5
Enter column count: 4
1 6 11 16
2 7 12 17
3 8 13 18
4 9 14 19
5 10 15 20
Original 2D array:
\ Column 0 1 2 3
Row \
0 1 6 11 16
1 2 7 12 17
2 3 8 13 18
3 4 9 14 19
4 5 10 15 20
Sorted 2D array:
\ Column 0 1 2 3
Row \
0 1 2 3 4
1 5 6 7 8
2 9 10 11 12
3 13 14 15 16
4 17 18 19 20
Transposed sorted 2D array:
\ Column 0 1 2 3 4
Row \
0 1 5 9 13 17
1 2 6 10 14 18
2 3 7 11 15 19
3 4 8 12 16 20
Transposed sorted 2D array is what you want to get as the output (based on my understanding of your question).
Also, there is a function at the top, getDigitCount for calculating the maximum number of digits a number has in between all user-provided numbers for string formatting purposes (using std::setw).

From what I understand, you want something as below :
1 5 6
2 8 4
9 7 3
to be sorted into :
1 2 3
4 5 6
7 8 9
the most simplest way would be u have to map the 2-D array into a 1-D array - “1 5 6 2 8 4 9 7 3”, sort them using most optimal algorithm. which would return “ 1 2 3 4 5 6 7 8 9 “ , and then map it back to 2-D array from 1-D array.
In effect you could achieve any sort of ordering, it just depends on your mapping.
You could even achieve something like this
1 4 7
2 5 8
3 6 9
What you need is the mapping from 2-D to 1-D.

Related

swap all elements from opposite lines in a C ++ matrix

I would like to change each element of the matrix with its "opposite" (element 0,0 becomes element n, n element 0,1 becomes n, n-1 and etc ..).
below an example:
1 2 3 9 8 7
4 5 6 --> 6 5 4
7 8 9 3 2 1
or:
4 5 4 7 22 14 12 2
5 2 6 8 ---> 2 4 6 2
2 6 4 2 8 6 2 5
2 12 14 22 7 4 5 4
anyone have any ideas on how to do it?
It is enough to use the standard algorithm std::reverse to perform the task.
Here is a demonstration program.
#include <iostream>
#include <iterator>
#include <algorithm>
int main()
{
const size_t N1 = 3;
int a[N1][N1] =
{
{ 1, 2, 3 },
{ 4, 5, 6 },
{ 7, 8, 9 }
};
std::reverse( std::begin( a ), std::end( a ) );
for ( auto &row : a )
{
std::reverse( std::begin( row ), std::end( row ) );
}
for (const auto &row : a)
{
for (const auto &item : row)
{
std::cout << item << ' ';
}
std::cout << '\n';
}
std::cout << '\n';
const size_t N2 = 4;
int b[N2][N2] =
{
{ 4, 5, 4, 7 },
{ 5, 2, 6, 8,},
{ 2, 6, 4, 2 },
{ 2, 12, 14, 22 }
};
std::reverse( std::begin( b ), std::end( b ) );
for (auto &row : b)
{
std::reverse( std::begin( row ), std::end( row ) );
}
for (const auto &row : b)
{
for (const auto &item : row)
{
std::cout << item << ' ';
}
std::cout << '\n';
}
std::cout << '\n';
}
The program output is
9 8 7
6 5 4
3 2 1
22 14 12 2
2 4 6 2
8 6 2 5
7 4 5 4
You could write a separate function to perform such an operation like
template <typename T, size_t N>
void reverse_matrix( T ( &a )[N][N] )
{
std::reverse( std::begin( a ), std::end( a ) );
for (auto &row : a)
{
std::reverse( std::begin( row ), std::end( row ) );
}
}
Another approach is to reinterpret the two-dimensional arrays as ine-dimensional arrays like
std::reverse( std::begin( reinterpret_cast< int ( & )[N1 * N1] > ( a ) ),
std::end( reinterpret_cast< int ( & )[N1 * N1] >( a ) ) );
and
std::reverse( std::begin( reinterpret_cast< int ( & )[N2 * N2] > ( b ) ),
std::end( reinterpret_cast< int ( & )[N2 * N2] >( b ) ) );
Without using the standard algorithm std::reverse you will need to use loops as for example
for ( size_t i = 0; i < N1 / 2; i++ )
{
std::swap( a[i], a[N1-i-1] );
}
for ( size_t i = 0; i < N1; i++ )
{
for ( size_t j = 0; j < N1 / 2; j++ )
{
std::swap( a[i][j], a[i][N1-j-1] );
}
}
You can do it simply with for loop. This is code:
#include <iostream>
using namespace std;
int main(){
int n;
cin>>n;
int arr[n][n], arr1[n][n];
for(int i = 0; i < n; i++){
for(int j = 0; j < n; j++)
cin>>arr[i][j];
}
for(int i = 0; i < n; i++){
for(int j = 0; j < n; j++)
arr1[i][j] = arr[n-1-i][n-1-j];
}
for(int i = 0; i < n; i++){
for(int j = 0; j < n; j++){
cout<<arr1[i][j]<<" ";
}
cout<<endl;
}
}

Inputting multiple integers from lines into a 2d array c++

I initialized a 2d array and am trying to fill the array respectively. My issue is I cannot get the 2d array to update.
Input is:
0 1 9
0 4 8
1 5 5
2 0 6
3 2 2
1 3 1
2 1 3
4 3 7
5 3 4
My code is:
stringstream s(input);
while(count != numV){
getline(cin, input);
while(s >> u >> v >> weight)
Graph[u][v] = weight;
count++;
}
You have to make the input stringstream after scanning the input, So your code should be
while(count != numV){
getline(cin, input);
stringstream s(input);
while(s >> u >> v >> weight)
Graph[u][v] = weight;
count++;
}
Note that you don't have to use arrays for storing the information(like int values) in 2D manner because you can also use dynamically sized containers like std::vector as shown below. The advantage of using std::vector is that you don't have to know the number of rows and columns beforehand in your input file. So you don't have to allocate memory beforehand for rows and columns. You can add the values dynamically. The below program read data(int values) from input.txt and store those in a 2D vector.
#include <iostream>
#include <vector>
#include <string>
#include <sstream>
#include<fstream>
int main() {
std::string line;
int word;
std::ifstream inFile("input.txt");
//create/use a std::vector instead of builit in array
std::vector<std::vector<int>> vec;
if(inFile)
{
while(getline(inFile, line, '\n'))
{
//create a temporary vector that will contain all the columns
std::vector<int> tempVec;
std::istringstream ss(line);
//read word by word(or int by int)
while(ss >> word)
{
//std::cout<<"word:"<<word<<std::endl;
//add the word to the temporary vector
tempVec.push_back(word);
}
//now all the words from the current line has been added to the temporary vector
vec.emplace_back(tempVec);
}
}
else
{
std::cout<<"file cannot be opened"<<std::endl;
}
inFile.close();
//lets check out the elements of the 2D vector so the we can confirm if it contains all the right elements(rows and columns)
for(std::vector<int> &newvec: vec)
{
for(const int &elem: newvec)
{
std::cout<<elem<<" ";
}
std::cout<<std::endl;
}
return 0;
}
The output of the above program can be seen here. The input file through which int values are read is also given at the above mentioned link.
If you want to take input using std::cin instead of std::ifstream then you just need to change the line while(getline(inputFile, line, '\n')) to :
while(getline(std::cin, line, '\n'))
And also remove other references to inputFile. The logic remains the same. IMO reading from file saves time and effort since the user don't have to write the inputs again and again into the console.
Here is the full solution plus a print function:
#include <iostream>
#include <iomanip>
#include <sstream>
#include <tuple>
inline static constexpr size_t ROW_COUNT { 7 };
inline static constexpr size_t COL_COUNT { 7 };
void printGraph( int (&graph)[ ROW_COUNT ][ COL_COUNT ], const std::tuple< size_t, size_t >& dimensions, int maxDigitCount );
int getDigitCount( int num );
int main( )
{
int Graph[ ROW_COUNT ][ COL_COUNT ] { };
int numV { 9 };
int count { };
int maxDigitCount { };
while( count != numV )
{
std::string input;
std::getline( std::cin, input );
std::stringstream ss( input );
int u { };
int v { };
int weight { };
while ( ss >> u >> v >> weight )
{
Graph[u][v] = weight;
if ( getDigitCount( weight ) > maxDigitCount )
{
maxDigitCount = getDigitCount( weight );
}
}
++count;
}
constexpr std::tuple< size_t, size_t > dimensions( ROW_COUNT, COL_COUNT );
printGraph( Graph, dimensions, maxDigitCount );
}
int getDigitCount( int num )
{
num = abs( num );
return ( num < 10 ? 1 :
( num < 100 ? 2 :
( num < 1000 ? 3 :
( num < 10'000 ? 4 :
( num < 100'000 ? 5 :
( num < 1'000'000 ? 6 :
( num < 10'000'000 ? 7 :
( num < 100'000'000 ? 8 :
( num < 1'000'000'000 ? 9 :
10 )))))))));
}
void printGraph( int (&graph)[ ROW_COUNT ][ COL_COUNT ], const std::tuple< size_t, size_t >& dimensions, int maxDigitCount )
{
std::cout << "\nGraph data:\n" << '\n' << " \\ Column ";
for ( size_t col = 0; col < std::get<1>( dimensions ); ++col )
{
std::cout << std::left << std::setw( maxDigitCount + 2 ) << std::setfill(' ') << col;
}
std::cout << '\n' << "Row \\" << '\n' << '\n';
for ( size_t row = 0; row < std::get<0>( dimensions ); ++row )
{
std::cout << " " << row << " ";
for ( size_t col = 0; col < std::get<1>( dimensions ); ++col )
{
std::cout << std::left << std::setw( maxDigitCount + 2 ) << std::setfill(' ') << graph[ row ][ col ];
}
std::cout << '\n' << '\n';
}
}
This will give you a result like this:
0 1 9
0 4 8
1 5 55
2 0 6
3 2 2
1 3 112
2 1 3
4 3 7832
5 3 4
Graph data:
\ Column 0 1 2 3 4 5 6
Row \
0 0 9 0 0 8 0 0
1 0 0 0 112 0 55 0
2 6 3 0 0 0 0 0
3 0 0 2 0 0 0 0
4 0 0 0 7832 0 0 0
5 0 0 0 4 0 0 0
6 0 0 0 0 0 0 0
Hopefully this is what you need.

printing stack in the incorrect order in c++

I have a function that pushes down all non zero integers to the top of my array and then reprints it in a 3x3 matrix.
the problem i am having is when i push all the non zero integers into my stack it reverses the order.
** the indexing of my array is backwards. ie, in a 3x3 matrix the coordinates (0,0) would be the bottom left **
here is the relevant code:
void State::pushDown() {
std::stack<int> tempStack;
for ( int c = 0; c < BOARDSIZE; c++ )
{
for ( int r = 0; r < BOARDSIZE ; r++ )
{
if ( grid[r][c] != 0 ) tempStack.push( grid[r][c] );
}
for ( int r = BOARDSIZE; r != 0; --r )
{
if ( !tempStack.empty() )
{
grid[r-1][c] = tempStack.top();
tempStack.pop();
}
else
{
grid[r-1][c] = 0;
}
}
}
}
State() {
for (int i = 0; i < BOARDSIZE; i++)
for (int j = 0; j < BOARDSIZE; j++)
grid[i][j] = rand() % 7;
}
void State::printBoard() {
cout << endl;
for (int i = 0; i < BOARDSIZE; i++) {
for (int j = 0; j < BOARDSIZE; j++) {
cout << " " << grid[BOARDSIZE - i - 1][j] << " ";
}
cout << endl;
}
}
int main() {
srand(time(0));
State state;
state.printBoard();
state.pushDown();
state.printBoard();
return 0;
}
here is my current output:
before push down function
045
504
226
after push down function:
006
224
545
as you can see it successfully pushes the non zero elements to the bottom of the matrix however in the process it reverses the order of the other numbers and i believe this is because of the stack.
my expected output would be the following:
before push down function
045
504
226
after push down function:
005
544
226
My question is- how can i fix my function so that the order of the elements remain the same without reversing.
Here is a demonstrative program that shows how the loops can be defined.
#include <iostream>
#include <stack>
const int BOARDSIZE = 3;
void reformat( int ( &a )[BOARDSIZE][BOARDSIZE] )
{
std::stack<int> tempStack;
for ( int c = 0; c < BOARDSIZE; c++ )
{
for ( int r = 0; r < BOARDSIZE ; r++ )
{
if ( a[r][c] != 0 ) tempStack.push( a[r][c] );
}
for ( int r = BOARDSIZE; r != 0; --r )
{
if ( !tempStack.empty() )
{
a[r-1][c] = tempStack.top();
tempStack.pop();
}
else
{
a[r-1][c] = 0;
}
}
}
}
int main()
{
int a[BOARDSIZE][BOARDSIZE] =
{
{ 0, 4, 5 },
{ 5, 0, 4 },
{ 2, 2, 6 }
};
for ( const auto &row : a )
{
for ( const auto &item : row ) std::cout << item << ' ';
std::cout << '\n';
}
std::cout << '\n';
reformat( a );
for ( const auto &row : a )
{
for ( const auto &item : row ) std::cout << item << ' ';
std::cout << '\n';
}
std::cout << '\n';
return 0;
}
Its output is
0 4 5
5 0 4
2 2 6
0 0 5
5 4 4
2 2 6
If you are outputting the array starting from its last row then use the following loops
#include <iostream>
#include <stack>
const int BOARDSIZE = 3;
void reformat( int ( &a )[BOARDSIZE][BOARDSIZE] )
{
std::stack<int> tempStack;
for ( int c = 0; c < BOARDSIZE; c++ )
{
for ( int r = 0; r < BOARDSIZE ; r++ )
{
if ( a[BOARDSIZE-r-1][c] != 0 ) tempStack.push( a[BOARDSIZE-r-1][c] );
}
for ( int r = 0; r != BOARDSIZE; ++r )
{
if ( !tempStack.empty() )
{
a[r][c] = tempStack.top();
tempStack.pop();
}
else
{
a[r][c] = 0;
}
}
}
}
int main()
{
int a[BOARDSIZE][BOARDSIZE] =
{
{ 2, 2, 6 },
{ 5, 0, 4 },
{ 0, 4, 5 }
};
for ( size_t i = 0; i < BOARDSIZE; i++ )
{
for ( const auto &item : a[BOARDSIZE - i - 1] ) std::cout << item << ' ';
std::cout << '\n';
}
std::cout << '\n';
reformat( a );
for ( size_t i = 0; i < BOARDSIZE; i++ )
{
for ( const auto &item : a[BOARDSIZE - i - 1] ) std::cout << item << ' ';
std::cout << '\n';
}
std::cout << '\n';
return 0;
}
The program output is the same as shown above
0 4 5
5 0 4
2 2 6
0 0 5
5 4 4
2 2 6
But now the array is outputted starting from its last line.

How can i examine all rows in c++?

You can see my input and output: https://imgur.com/ZT8zPnW
In the first line 3 means how many line has, and the 5 means how many data has in each line, after that I uploaded the array. In the output i wrote the line id, minimum and maximum data.
My task is that where the minimum data is bigger than the maximum.
for (int i = 0; i < n; i++)
{
if(t[i].min > t[i].max)
{
cout << t[i].id;
}
}
But i have this code and it can examine the min and max data line by line. But the correct answer line 3, beacuse in line 3 min data(16) is bigger than line 1 max data(15)
If I have understood the question correctly you need something like the following
#include <iostream>
#include <utility>
#include <iterator>
#include <algorithm>
int main()
{
const size_t M = 3, N = 5;
int a[M][N] =
{
{ 10, 15, 12, 10, 10 },
{ 11, 11, 11, 11, 20 },
{ 18, 16, 16, 16, 20 }
};
std::pair<size_t, size_t> row = { 0, 0 };
auto p = std::minmax_element( std::begin( a[0] ), std::end( a[0] ) );
std::pair<int, int> minmax = { *p.first, *p.second };
for ( size_t i = 1; !( minmax.second < minmax.first ) && ( i < M ); i++ )
{
auto p = std::minmax_element( std::begin( a[i] ), std::end( a[i] ) );
if ( minmax.first < *p.first )
{
minmax.first = *p.first;
row.first = i;
}
if ( *p.second < minmax.second )
{
minmax.second = *p.second;
row.second = i;
}
}
if ( minmax.second < minmax.first )
{
std::cout << "The minimum " << minmax.first
<< " in the row " << row.first
<< " is greater than the maximum " << minmax.second
<< " in row " << row.second << '\n';
}
return 0;
}
The demonstrative program output is
The minimum 16 in the row 2 is greater than the maximum 15 in row 0
Or in the output statement you can use expressions row.first + 1 and row.second + 1 to get the output like
The minimum 16 in the row 3 is greater than the maximum 15 in row 1
If the program is too complucated to your level of knowledge then here is a simplifed program that uses a user-defined function minmax_element. All you need to know is the standard class std::pair. It is just a class of two elements with names first and second.
#include <iostream>
#include <utility>
std::pair<size_t, size_t> minmax_element( const int *a, size_t n )
{
std::pair<size_t, size_t> minmax = { 0, 0 };
for ( size_t i = 1; i < n; i++ )
{
if ( a[i] < a[minmax.first] ) minmax.first = i;
else if ( a[minmax.second] < a[i] ) minmax.second = i;
}
return minmax;
}
int main()
{
const size_t M = 3, N = 5;
int a[M][N] =
{
{ 10, 15, 12, 10, 10 },
{ 11, 11, 11, 11, 20 },
{ 18, 16, 16, 16, 20 }
};
std::pair<size_t, size_t> row = { 0, 0 };
auto minmax = minmax_element( a[0], N );
for ( size_t i = 1; !( a[row.second][minmax.second] < a[row.first][minmax.first] ) &&
( i < M ); i++ )
{
auto local_minmax = minmax_element( a[i], N );
if ( a[row.first][minmax.first] < a[i][local_minmax.first] )
{
minmax.first = local_minmax.first;
row.first = i;
}
if ( a[i][local_minmax.second] < a[row.second][minmax.second] )
{
minmax.second = local_minmax.second;
row.second = i;
}
}
if ( a[row.second][minmax.second] < a[row.first][minmax.first] )
{
std::cout << "The minimum " << a[row.first][minmax.first]
<< " in the row " << row.first
<< " is greater than the maximum " << a[row.second][minmax.second]
<< " in row " << row.second << '\n';
}
return 0;
}

displaying a vector of deques in columns

I'm trying to display a vector of deques (std::vector<std::deque<int>> v) like this
v.at(0).at(0) v.at(1).at(0) v.at(2).at(0) v.at(3).at(0)
v.at(0).at(1) v.at(1).at(1) v.at(2).at(1) v.at(3).at(1)
v.at(0).at(2) v.at(1).at(2) v.at(2).at(2) v.at(3).at(2)
v.at(1).at(3) v.at(3).at(3)
v.at(3).at(4)
The first part of the vector is fixed at 7, the size of the actual columns are dynamic however depending on what the user chooses to do.
I was attempting something like
int row = 0;
int column;
for (column = 0; column < v.at(row).size(); column++){
cout << "v["<< row <<"]["<< column << "]" << v.at(row).at(column) << "\t";
while (row < v.size()){
cout << endl;
row++;
}
}
I'm getting errors like
libc++abi.dylib: terminating with uncaught exception of type std::out_of_range: vector
make: *** [Pile.h] Abort trap: 6
Having one of those blah brain days. Can someone help me print this out the way I want it?
Here is a demonstrative program that shows one of approaches to the task.
#include <iostream>
#include <iomanip>
#include <vector>
#include <deque>
#include <algorithm>
int main()
{
std::vector<std::deque<int>> v =
{
{ 0, 1, 2 },
{ 0, 1, 2, 3 },
{ 0, 1, 2 },
{ 0, 1, 2, 3, 4 }
};
size_t n = std::max_element( v.begin(), v.end(),
[]( const auto &x, const auto &y )
{
return x.size() < y.size();
} )->size();
for ( size_t i = 0; i < n; i++)
{
for ( size_t j = 0; j < v.size(); j++ )
{
std::cout << std::setw( 4 );
if ( i < v[j].size() )
{
std::cout << v[j][i];
}
else
{
std::cout << "";
}
}
std::cout << std::endl;
}
return 0;
}
Its output is
0 0 0 0
1 1 1 1
2 2 2 2
3 3
4
First of all, I suggest to get the max queue size
std::size_t maxQ { 0U };
for ( auto const & q : v )
maxQ = std::max(maxQ, q.size());
Now you can write a loop over (0U, maxQ( (the loop of lines) writing elements when available and space otherwise.
for ( auto i = 0U ; i < maxQ ; ++i )
{
for ( auto j = 0U ; j < v.size() ; ++j )
if ( i < v[j].size() )
; // print v[j][i]
else
; // print space
std::cout << std::endl; // endl of line
}
I leave to you cells printing details