Home > Back-end >  Integer input from user
Integer input from user

Time:12-28

I am writing a program in C that requires taking in integers from the user.

These may come in one of two forms:

  1. Single-input integers of the form 'X\n', where X is the user input. These get put into regular integer primitives.

  2. Multi-input integers of the form 'X X X X X\n', where X is the user input. These are parsed into an array of integers.

Here is an example of each:

Multi-input line

void UI::inputMatrix(Entries** matrix, int rows, int cols){
    for (int i = 0 ; i < rows; i  ){
        std::cout << "Row " << i 1 << ": ";
        for (int j = 0 ; j < cols ; j  ){
            std::cin >> matrix[i][j];
        }
    }
    std::cout << endl;
}

Single-input line

    std::cout << std::endl << "Please input the digit corresponding to your option: ";
    std::cin >> m_operation;

I've found that with std::cin functionality, this works perfectly fine unless the user begins to (a) not follow instructions or (b) type non-sensical input.

What is the best way to take this sort of integer input from the user?

I am considering writing my own program that parses string input from the user using std::getline() into the integers I require, and throws an error otherwise, but I really like the std::cin functionality available for taking in inputs into my array.

UPDATE:

Here is my solution:

istringstream readInput(){
    
    string s;
    std::cin.ignore(std::numeric_limits<std::streamsize>::max(), '\n');
    getline(cin, s);
    istringstream buffer(s);
    
    return buffer;
}

The istringstream can be used to put inputs into the designated locations and also acts as a boolean if an unexpected input is encountered.

CodePudding user response:

A good way to parse line-based input is to read lines using std::getline and then use std::istringstream to read formatted input from each line the same way you would do with std::cin.

For example:

#include <iostream>
#include <sstream>
#include <string>

int main()
{
    int line_num = 1;
    for (std::string line; std::getline(std::cin, line);   line_num)
    {
        std::istringstream iss(line);
        for (int value; iss >> value; )
        {
            std::cout << "Line " << line_num << ": " << value << "\n";
        }
    }
}

Input:

1 2
3 4 5 fail 6
7
nope
8

Output:

Line 1: 1
Line 1: 2
Line 2: 3
Line 2: 4
Line 2: 5
Line 3: 7
Line 5: 8

CodePudding user response:

I came across this problem before, and the cin behavior really confuses me, if cin tries to read alpha into an integer, cin will not read until you manually use clear() function or another trick.

So here is my solution, it just works, maybe not elegant :)

vector<int> matrix(size);
int temp;

while (cin >> temp)
{
  matrix.push_back(temp);
  if (cin.peek() == '\n') break;
}
cin.clear();
  •  Tags:  
  • c
  • Related