Как выйти, пока cin l oop после ввода значения non-numberri c в самом конце? - PullRequest
0 голосов
/ 24 апреля 2020

Этот код принимает несколько целых и помещает его в вектор при нажатии клавиши «Ввод». Выходные данные показывают все элементы в векторе; каждый элемент разделен запятыми. Проблема в том, что клавиша «Ввод» не выходит из , пока cin l oop, когда я вводю букву или пробел в конце. Например:

Ввод: 4 55 6 2 1g // нажатие клавиши ввода приведет к go к следующей строке и не прерывает while-l oop

Как это обычно работает:

Ввод: 4 55g 6 2 1 // Если я нажму ввод, здесь будет игнорироваться "g" и выведите числовые элементы из вектора, разделенные запятой, чего я и хочу, но этого не произойдет, если «g» находится в самом конце

Вывод: 4, 55, 6, 2, 1

Проблема состоит только в том, что я ввожу не числовой c ввод в конце, а не между элементами. Нажатие пробела в конце также вызывает проблему

int main() {

vector<int> myv;
int value = 0;

while (cin >> value){
    myv.push_back(value);
    if (cin.get() == '\n'){
        break;
    }
}

auto iter = myv.begin();
    while(true){
        cout << *iter;
        ++iter;
        if(iter == myv.end()){
            break;
        }
        else{
            cout << ", ";
        }
    }
}

1 Ответ

0 голосов
/ 24 апреля 2020

Ваши самые большие проблемы были:
- Буква, которую вы ввели непосредственно перед нажатием Enter, все еще находится в потоке. Таким образом, ваш std::cin.get() чек не идентифицирует клавишу Enter, но вместо этого идентифицирует букву.
- Вы вернулись к своему вектору, прежде чем проверять, должны ли вы это иметь. Эти буквы входят в ваш вектор.

Этот код более сложен из-за того, что возникает желание ввести данные сразу в одну строку и обработать их после факта. Поэтому я просто читаю строку с использованием std::getline() и обрабатываю этот общий ввод в функции break_up(). На данный момент у меня есть вектор строк, содержащий все отдельные части, которые были введены, действительные или нет.

Наконец, куски проверяются на достоверность. Как только фрагмент, который не может быть полностью преобразован в целое число, myv прекращает прием данных. Тогда это напечатано. Я заменил ваше время l oop на более короткое для l oop.

Если каждый фрагмент данных был введен индивидуально и проверен на ходу, то эта программа становится намного проще. Самый сложный момент разрыва линии пропадает, и вы можете проверить, как вы go, и остановиться точно, когда обнаружите неверные данные, в отличие от ввода тонны данных, просто чтобы обнаружить, что 80% из них не были добавлены .

#include <iostream>
#include <string>
#include <vector>

std::vector<std::string> break_up(std::string line) {
  std::vector<std::string> chunks;

  // Emtpy line check
  if (line.length()) {
    std::string::size_type loc = 0;
    std::string::size_type subStart = 0;
    while (loc != std::string::npos) {
      loc = line.find_first_of(" \t\r\n", loc + 1);
      loc != std::string::npos
          ? chunks.push_back(line.substr(subStart, loc - subStart))
          : chunks.push_back(line.substr(subStart));  // catches last item
      subStart = loc + 1;
    }
  }

  return chunks;
}

int main() {
  std::vector<int> myv;
  std::string values;  // Changed type

  std::getline(std::cin, values);
  std::vector<std::string> chunks = break_up(values);

  for (auto i : chunks) {
    // std::size_t pos;
    try {
      int num = std::stoi(i); // , &pos);
      // if (pos == i.length()) {
        myv.push_back(num);
      // } else {
      //   break;  // Remove this else block to add all valid numbers that
      // }         // were entered
    } catch (...) {
    }  // std::stoi throws two exceptions, don't need to
       // distinguish or take any action. Just don't want the program ending
  }

  // Replaced unnecessarily complicated while loop
  for (unsigned int i = 0; i < myv.size(); ++i) {
    std::cout << myv[i];
    if (i < myv.size() - 1) {
      std::cout << ", ";
    }
  }
  std::cout << '\n';
}

РЕДАКТИРОВАТЬ : Я внес некоторые небольшие изменения в код, чтобы устранить недопонимание того, что является желаемым результатом. Я оставил старый код закомментированным.

...