Nano Hash - криптовалюты, майнинг, программирование

Почему getline читает только первый штрих?

Моя программа должна читать команды и выполнять их одним числом. Он должен +, -, /, * номер, но он читает только первый штрих.

    ifstream fin("file.txt");
    string line;
    while(getline(fin,line))
    {
        if(line[0] == '+')
        {
            for(int i = 1; i < 10; i++)
            {
                n += line[i];
            }
            ss << n;
            double p = 0.0;
            ss >> p;
            res += p;
        }
        n = "";
        if(line[0] == '-')
        {
            for(int i = 1; i < 10; i++)
            {
                n += line[i];
            }
            ss << n;
            double m = 0.0;
            ss >> m;
            res -= m;
        }
        n = "";
        if(line[0] == '*')
        {
            for(int i = 1; i < 10; i++)
            {
                n += line[i];
            }
            ss << n;
            double di = 0.0;
            ss >> di;
            res *= di;
        }
        n = "";
        if(line[0] == '/')
        {
            for(int i = 1; i < 10; i++)
            {
                n += line[i];
            }
            ss << n;
            double mu = 0.0;
            ss >> mu;
            res /= mu;
        }
        n = "";
    }

пример файла:

+1
-2
*5

выход:

1

Ожидаемый вывод равен -5, но выводится 1. Почему это происходит и что мне делать? ss — строковый поток, n — строка, res — двойное число, strokes[] — строки.

05.06.2021

  • Ваш минимально воспроизводимый пример не воспроизводим. Что такое ss? n? res? Почему вы зацикливаетесь после определения операции? 05.06.2021
  • отредактированный вопрос 05.06.2021
  • Включите соответствующий код. Прочитайте ссылку, которую я разместил. 05.06.2021
  • Я могу сделать еще несколько предположений, достаточно, чтобы сказать, что вы значительно усложнили свое решение, но недостаточно, чтобы дать фактический ответ. Вот почему так важно научиться правильно задавать вопросы. Он избегает бесполезных движений туда-сюда и сразу переходит к делу. Я также рекомендую снова прочитать Как спросить. Скажу, что для первого раза неплохо. 05.06.2021
  • p = n; будет намного проще. А еще проще: res += n;, без промежуточной переменной и принудительных преобразований. 05.06.2021

Ответы:


1

Вы уже узнали сами. Вы должны либо очистить std::istringstream, либо определить новый, даже с тем же именем. Итак, вы можете написать

    ss.clear(); // Clear EOF bit
    ss.str(std::string()); // Clear buffer

перед следующей операцией вставки, или вы просто каждый раз определяете новую переменную, написав:

    std::stringstream ss{};
    ss << n;

Я также изменил ваш код на минимальный воспроизводимый пример:

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

int main() {

    std::string line{};
    std::stringstream ss{};
    std::string n{};
    double res{};

    std::ifstream fin("file.txt");

    while (std::getline(fin, line))
    {
        if (line[0] == '+')
        {
            for (int i = 1; i < line.length(); i++)
            {
                n += line[i];
            }
            ss << n;
            double p = 0.0;
            ss >> p;
            res += p;
        }
        n = "";
        if (line[0] == '-')
        {
            for (int i = 1; i < line.length(); i++)
            {
                n += line[i];
            }
            ss.clear(); // Clear EOF bit
            ss.str(std::string()); // Clear buffer
            ss << n;
            double m = 0.0;
            ss >> m;
            res -= m;
        }
        n = "";
        if (line[0] == '*')
        {
            for (int i = 1; i < line.length(); i++)
            {
                n += line[i];
            }
            ss.clear(); // Clear EOF bit
            ss.str(std::string()); // Clear buffer
            ss << n;
            double di = 0.0;
            ss >> di;
            res *= di;
        }
        n = "";
        if (line[0] == '/')
        {
            for (int i = 1; i < line.length(); i++)
            {
                n += line[i];
            }
            ss.clear(); // Clear EOF bit
            ss.str(std::string()); // Clear buffer
            ss << n;
            double mu = 0.0;
            ss >> mu;
            res /= mu;
        }
        n = "";
    }
    std::cout << res;
    return 0;
}

И я добавил код с немного более современным C++:

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

int main() {
    
    if (std::ifstream ifs{ "file.txt" }; ifs) {

        double result{};
        for (std::string line{}; std::getline(ifs, line); ) {

            char calculationOperator{};
            double number{};

            std::istringstream iss{ line };
            if (iss >> calculationOperator >> number) {

                switch (calculationOperator) {
                case '+':
                    result += number;
                    break;
                case '-':
                    result -= number;
                    break;
                case '*':
                    result *= number;
                    break;
                case '/':
                    result /= number;
                    break;
                default:
                    std::cerr << "\n\nError: invalid mathematical operator '" << calculationOperator << "' found\n\n";
                }
            }
            else
                std::cerr << "\n\nError: Wronng input in line: " << line << "\n\n";
        }
        std::cout << "\n\nResult:  " << result << "\n\n";
    }
    else
        std::cerr << "\n\nError: Could not open 'file.txt'\n\n";
    return 0;
}
05.06.2021
Новые материалы

Кластеризация: более глубокий взгляд
Кластеризация — это метод обучения без учителя, в котором мы пытаемся найти группы в наборе данных на основе некоторых известных или неизвестных свойств, которые могут существовать. Независимо от..

Как написать эффективное резюме
Предложения по дизайну и макету, чтобы представить себя профессионально Вам не позвонили на собеседование после того, как вы несколько раз подали заявку на работу своей мечты? У вас может..

Частный метод Python: улучшение инкапсуляции и безопасности
Введение Python — универсальный и мощный язык программирования, известный своей простотой и удобством использования. Одной из ключевых особенностей, отличающих Python от других языков, является..

Как я автоматизирую тестирование с помощью Jest
Шутка для победы, когда дело касается автоматизации тестирования Одной очень важной частью разработки программного обеспечения является автоматизация тестирования, поскольку она создает..

Работа с векторными символическими архитектурами, часть 4 (искусственный интеллект)
Hyperseed: неконтролируемое обучение с векторными символическими архитектурами (arXiv) Автор: Евгений Осипов , Сачин Кахавала , Диланта Хапутантри , Тимал Кемпития , Дасвин Де Сильва ,..

Понимание расстояния Вассерштейна: мощная метрика в машинном обучении
В обширной области машинного обучения часто возникает необходимость сравнивать и измерять различия между распределениями вероятностей. Традиционные метрики расстояния, такие как евклидово..

Обеспечение масштабируемости LLM: облачный анализ с помощью AWS Fargate и Copilot
В динамичной области искусственного интеллекта все большее распространение получают модели больших языков (LLM). Они жизненно важны для различных приложений, таких как интеллектуальные..