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.
Related
Given two arrays, first has 'n' numbers and the second one has 'n-m' numbers; the second array is not in the same order as the first. If there are several numbers with the same value, they end up in the order of the positions in the original array. Also, all the values from the second array are also found in the first array. I have to find the 'm' missing numbers in the order in which they appear in the first array.
input:
7 3
12 34 45 29 100 87 32
100 87 12 34
output:
45 29 32
#include <iostream>
using namespace std;
int main()
{
int n, missing_number = 0, m, i, j, v[1201], w[1201];
cin >> n >> m;
for (i = 0; i < n; ++i) {
cin >> v[i];
}
for (i = 0; i < n - m; ++i) {
cin >> w[i];
}
for (i = 0; i < n; ++i) {
missing_number = 1;
for (j = 0; j < n - m; ++j) {
if (v[i] == w[j]) {
missing_number = -1;
}
}
if (missing_number == 1) {
cout << v[i] << " ";
}
}
if (m == 0)
cout << "there are no missing numbers";
return 0;
}
my code doesn't work for repeating numbers like:
7 3
2 6 1 9 3 2 4
4 1 2 3
where my output should be:
6 9 2
Your program seems to be outputting the correct result. However, I felt that I need to refactor your code to improve its readability and remove the bad practices used in it.
The below is the same as your code with a bit of improvement:
#include <iostream>
#include <array>
#include <limits>
int main( )
{
std::array<int, 1201> arr1; // use std::array instead of raw arrays
std::array<int, 1201> arr2;
std::size_t arr1_size { }; // renamed n
std::size_t arr2_size { }; // renamed m
std::cin >> arr1_size >> arr2_size;
if ( arr2_size == 0 ) // this if statement should be here to help end
{ // the program early on to prevent the execution
// of the for-loops
std::cout << "There are no missing numbers.\n";
return 0;
}
for ( std::size_t idx { }; idx < arr1_size; ++idx ) // use std::size_t
{ // for the loop counters
std::cin >> arr1[ idx ];
}
for ( std::size_t idx { }; idx < arr1_size - arr2_size; ++idx )
{
std::cin >> arr2[ idx ];
}
for ( std::size_t arr1_idx { }; arr1_idx < arr1_size; ++arr1_idx )
{
bool isNumberMissing { true }; // this should be of type bool
for ( std::size_t arr2_idx { }; arr2_idx < arr1_size - arr2_size; ++arr2_idx )
{
if ( arr1[ arr1_idx ] == arr2[ arr2_idx ] )
{
isNumberMissing = false;
// this is my trick for solving your code's bug
arr2[ arr2_idx ] = std::numeric_limits<int>::min( );
break; // break here to improve performance
}
}
if ( isNumberMissing )
{
std::cout << arr1[ arr1_idx ] << " ";
}
}
std::cout << '\n';
}
Sample input/output #1:
7 3
12 34 45 29 100 87 32
100 87 12 34
45 29 32
Sample input/output #2:
7 3
2 6 1 9 3 2 4
4 1 2 3
6 9 2
Note: See Why is "using namespace std;" considered bad practice?
I want to create a project that will print the '|' character as 4 layers going 1 3 5 7 something like
|
|||
|||||
|||||||
I wrote a for loop for this and the code is here:
for (int i = 1; i <= 4; i++) {
//for loop for displaying space
for (int s = i; s < 4; s++) {
cout << " ";
}
//for loop to display star equal to row number
for (int j = 1; j <= (2 * i - 1); j++) {
cout << "|";
}
// ending line after each row
cout << "\n";
}
So how can I make a code that will take user input like
cout << "Please enter a row number \n" << "Please enter a column number" << endl;
and let say the user entered 2 as row number 2 as column number I want the output to be something like
|
|
|||||
|||||||
Deletes 2 '|' character from the 2nd row
First I think putting every character in a array like char arr[] = { '|' , '||' , '|||', '||||'}
and deleting according to user input but I failed. Any help?
Here is a solution:
#include <iostream>
#include <vector>
std::size_t getLayerCount( )
{
std::cout << "How many layers to print: ";
std::size_t layerCount { };
std::cin >> layerCount;
return layerCount;
}
std::vector< std::vector<char> > generateShape( const std::size_t layerCount )
{
const std::size_t MAX_CHAR_COUNT_IN_A_ROW { layerCount * 2 };
constexpr char spaceChar { ' ' };
std::vector< std::vector<char> > shape( layerCount, std::vector<char>( MAX_CHAR_COUNT_IN_A_ROW, spaceChar ) );
for ( std::size_t row { }; row < layerCount; ++row )
{
for ( std::size_t offset { layerCount - row - 1 }; offset < layerCount + row; ++offset )
{
shape[ row ][ offset ] = '|';
}
shape[ row ][ MAX_CHAR_COUNT_IN_A_ROW - 1 ] = '\0';
}
return shape;
}
void printShape( const std::vector< std::vector<char> >& shape )
{
for ( const auto& row : shape )
{
std::cout.write( row.data( ), row.size( ) ).write( "\n", 1 );
}
}
void deleteSpecificChars( std::vector< std::vector<char> >& shape )
{
std::cout << "Please enter a row number: ";
std::size_t rowNumber { };
std::cin >> rowNumber;
std::cout << "Please enter a column number: ";
std::size_t colNumber { };
std::cin >> colNumber;
--rowNumber;
--colNumber;
const std::size_t layerCount { shape.size( ) };
const std::size_t posOfFirstCharInRow { layerCount - rowNumber - 1 };
const std::size_t posOfTargetCharInRow { posOfFirstCharInRow + colNumber };
const std::size_t posOfLastCharInRow { posOfFirstCharInRow + ( 2 * rowNumber ) };
for ( std::size_t idx { posOfTargetCharInRow }; idx <= posOfLastCharInRow; ++idx )
{
shape[ rowNumber ][ idx ] = ' ';
}
}
int main( )
{
const std::size_t layerCount { getLayerCount( ) };
std::vector< std::vector<char> > shape { generateShape( layerCount ) };
printShape( shape );
deleteSpecificChars( shape );
printShape( shape );
return 0;
}
Sample input/output:
How many layers to print: 4
|
|||
|||||
|||||||
Please enter a row number: 2
Please enter a column number: 2
|
|
|||||
|||||||
Another one:
How many layers to print: 5
|
|||
|||||
|||||||
|||||||||
Please enter a row number: 4
Please enter a column number: 4
|
|||
|||||
|||
|||||||||
Limiting your pile of bars to 4 levels, this should work:
You basically just want a fixed size string of bars, '|'.
Then remove n consecutive characters from that string.
The only thing you have to calculate is the starting index to start removing from, then replace n characters with blanks.
You can add some checks for row and col boundaries.
[Demo]
#include <iostream> // cout
#include <string>
int main()
{
std::string bars(16, '|');
auto get_start_deleting_pos = [](int row, int col) {
if (row == 1) { if (col > 1) { return -1; } return 0; }
else if (row == 2) { if (col > 3) { return -1; } return col; }
else if (row == 3) { if (col > 5) { return -1; } return 3 + col; }
else if (row == 4) { if (col > 7) { return -1; } return 8 + col; }
else return -1;
};
auto print_bars = [&bars]() {
std::cout << " " << bars[0] << "\n";
std::cout << " " << bars.substr(1, 3) << "\n";
std::cout << " " << bars.substr(4, 5) << "\n";
std::cout << bars.substr(9) << "\n";
};
auto start_deleting_from_row{4};
auto start_deleting_from_col{1};
auto num_chars_to_delete{4};
auto pos{ get_start_deleting_pos(start_deleting_from_row, start_deleting_from_col) };
if (pos != -1)
{
bars.replace(pos, num_chars_to_delete, num_chars_to_delete, ' ');
}
print_bars();
}
And if you want a more generic solution, where the user inputs the level, the row and col to start deleting from, and the number of characters to delete:
[Demo]
#include <iostream> // cout
#include <string>
auto get_size_for_levels(int l) { return l*l; }
auto get_index_for_row_and_col(int row, int col) { return (row - 1) * (row - 1) - 1 + col; }
auto get_num_cols_for_row (int row) { return row * 2 - 1; }
auto check_row_and_col(int levels, int row, int col) {
if (row < 1 or levels < row) { return false; }
if (col < 1 or get_num_cols_for_row(row) < col) { return false; }
return true;
}
int main()
{
auto levels{7}; // levels start at 1
auto start_deleting_from_row{4}; // rows start at 1
auto start_deleting_from_col{5}; // cols start at 1
auto num_chars_to_delete{6};
std::string bars(get_size_for_levels(levels), '|');
if (check_row_and_col(levels, start_deleting_from_row, start_deleting_from_col))
{
bars.replace(
get_index_for_row_and_col(start_deleting_from_row, start_deleting_from_col),
num_chars_to_delete,
num_chars_to_delete,
' ');
}
for (int l{1}; l <= levels; ++l)
{
std::cout
<< std::string(levels - l, ' ')
<< bars.substr(get_index_for_row_and_col(l, 1), get_num_cols_for_row(l))
<< "\n";
}
}
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.
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 2 years ago.
Improve this question
As a result, the program must display the 3 largest elements of the sequence. Elements must be displayed from small to large and not using array...
Examples
Input:
3 1 2 3
Work result:
1 2 3
Input:
5 2 -4 16 0 15
Work result:
2 15 16
Input:
3 0 -1 -2
Work result:
-2 -1 0
Here is my code:
#include <iostream>
int main() {
int n;
std::cin >> n;
int number;
std::cin >> number;
int max1, max2, max3;
max1 = max2 = max3 = number;
for (int i = 1; i < n; i++) {
std::cin >> number;
if (number > max3) {
if (number > max2) {
if (number > max1) {
max3 = max2;
max2 = max1;
max1 = number;
} else {
max2 = number;
}
} else {
max3 = number;
}
}
}
std::cout << max3 << " " << max2 << " " << max1;
}
I'd use standard algorithms to keep it as simple as possible.
#include <algorithm>
#include <iostream>
#include <iterator>
#include <vector>
int main() {
std::vector<std::vector<int>> tests{
{5, 2, -4, 16, 0, 15},
{3, 0, -1, -2}
};
for(auto& test : tests) {
// sort the vector to get the three largest last
std::sort(test.begin(), test.end());
// create an iterator 3 steps back from the end
// (or less if the vector doesn't have 3 elements)
auto first = std::prev(test.cend(), std::min(test.size(), static_cast<size_t>(3)));
// copy to std::cout
std::copy(first, test.cend(), std::ostream_iterator<int>(std::cout, " "));
std::cout << '\n';
}
}
Output:
5 15 16
-1 0 3
A slightly more complicated way involves partially sorting the vector. This makes it more effective since you only need 3 elements sorted.
std::partial_sort puts the smallest elements first so we need to sort it in decending order (using std::greater<>).
#include <algorithm>
#include <iostream>
#include <iterator>
#include <vector>
int main() {
std::vector<std::vector<int>> tests{
{5, 2, -4, 16, 0, 15},
{3, 0, -1, -2}
};
for(auto& test : tests) {
// calculate how many elements to show, 0-3
auto elems = std::min(test.size(), static_cast<size_t>(3));
// sort "elems" elements in decending order
std::partial_sort(
test.begin(),
std::next(test.begin(), elems),
test.end(),
std::greater<>()
);
// copy the result to std::out, in reverse order since they are sorted "backwards"
std::copy(
std::prev(test.crend(), elems),
test.crend(),
std::ostream_iterator<int>(std::cout, " ")
);
std::cout << '\n';
}
}
My five cents.:)
#include <iostream>
#include <utility>
int main()
{
size_t n = 0;
int max1, max2, max3;
std::cin >> n;
size_t i = 0;
for ( int number; n-- && std::cin >> number; i = i < 3 ? i + 1 : i )
{
if ( i == 0 )
{
max3 = number;
}
else
{
if ( max3 < number )
{
std::swap( max3, number );
}
if ( i == 1 )
{
max2 = number;
}
else
{
if ( max2 < number )
{
std::swap( max2, number );
}
if ( i == 2 || max1 < number )
{
max1 = number;
}
}
}
}
if ( i > 0 )
{
std::cout << max3;
}
if ( i > 1 )
{
std::cout << ", " << max2;
}
if ( i > 2 )
{
std::cout << ", " << max1;
}
std::cout << '\n';
return 0;
}
If to enter
6
5 2 -4 16 0 15
then the output is
16, 15, 5
If to enter
6
-5 -2 4 -16 0 -15
then the output is
4, 0, -2
Or if to enter
4
3 0 -1 -2
then the program output is
3, 0, -1
Pay attention to that in general the user can enter less than 3 numbers.:)
The solution above allows duplicated maximum values.
If it is required that maximum values shall not be repeated then the program can look the following way.
#include <iostream>
#include <utility>
int main()
{
size_t n = 0;
int max1, max2, max3;
std::cin >> n;
size_t i = 0;
for ( int number; n-- && std::cin >> number; )
{
if ( i == 0 )
{
max3 = number;
i = 1;
}
else
{
if ( max3 < number )
{
std::swap( max3, number );
}
if ( number < max3 )
{
if ( i == 1 )
{
max2 = number;
i = 2;
}
else
{
if ( max2 < number )
{
std::swap( max2, number );
}
if ( number < max2 )
{
if ( i == 2 || max1 < number )
{
max1 = number;
i = 3;
}
}
}
}
}
}
if ( i > 0 )
{
std::cout << max3;
}
if ( i > 1 )
{
std::cout << ", " << max2;
}
if ( i > 2 )
{
std::cout << ", " << max1;
}
std::cout << '\n';
return 0;
}
For example if to enter
5
-1 -1 -1 -1 -1
where all numbers are equal each other then the output will contaoin onky one maximum number
-1
If to use standard containers then the standard container std::set is the most appropriate container.
For example
#include <iostream>
#include <set>
#include <iterator>
#include <algorithm>
int main()
{
size_t n = 0;
std::set<int> set;
std::cin >> n;
std::copy_n( std::istream_iterator<int>( std::cin ), n,
std::inserter( set, std::end( set ) ) );
size_t i = 3;
for ( auto it = std::rbegin( set ); i-- != 0 && it != std::rend( set ); ++it )
{
std::cout << *it << ' ';
}
std::cout << '\n';
return 0;
}
If to enter
6
5 2 -4 16 0 15
then the output is
16 15 5
int main () {
int n;
std::cin >> n;
int number;
std::cin >> number;
int max1, max2, max3;
max1 = max2 = max3 =number;
for(int i = 1; i < n; i++) {
std::cin >> number;
if (number > max3) {
if (number > max2) {
if (number > max1) {
max3 = max2;
max2 = max1;
max1 = number;
} else {
max3 = max2;
max2 = number;
}
} else {
max3 = number;
}
}
}
std::cout << max3 << " " << max2 << " " << max1;
}
If the number is greater than max2 but smaller than max1 then max2 is the new max3 and max2 is number, that was the mistake.
Do not write everything in main. Slice code to smaller pieces to make it easy to read.
Here is an example (a bit to fancy):
class AccumulateTopThree
{
public:
void update(int x)
{
if (!isUnique(x)) return;
keepInOrder(c, x);
keepInOrder(b, c);
keepInOrder(a, b);
}
void print(std::ostream& out)
{
// TODO: handle case when count of input nubers is less then 3
out << c << ' ' << b << ' ' << a << '\n';
}
private:
bool isUnique(int x) const
{
return a != x && b != x && c != x;
}
static void keepInOrder(int &a, int &b)
{
if (a < b) std::swap(a, b);
}
private:
int a = std::numeric_limits<int>::min();
int b = a;
int c = a;
};
https://wandbox.org/permlink/OFkQUaGI9PygAV6D
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