Форум программистов, компьютерный форум, киберфорум
С++ для начинающих
Войти
Регистрация
Восстановить пароль
Блоги Сообщество Поиск  
 
 
Рейтинг 4.63/40: Рейтинг темы: голосов - 40, средняя оценка - 4.63
 Аватар для Fixer_84
1505 / 969 / 812
Регистрация: 30.04.2016
Сообщений: 3,337

Обратная польская запись (ОПЗ). Учет приоритета операций

07.07.2018, 15:46. Показов 8537. Ответов 38
Метки нет (Все метки)

Студворк — интернет-сервис помощи студентам
Здравствуйте, уважаемые форумчане! Сегодня на курсах писали решение для задачи (см. ссылку на задачу), но, кажется, забыли, учесть приоритет операций (скобки в этой задаче отсутствуют по условию). Проблема всего в двух тестах (пишет неправильный ответ ) и скорее всего это приоритет. Может кто-то знает (уже сдавал эту задачу) как легко исправить данную ошибку или алгоритм переделывать придется И дело ли в этом вообще...непонятно. А так программа работает.

Вот код:

C++
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
#include <bits/stdc++.h>
 
    using namespace std;
 
int main() {
    int a, b;
    bool flag = false;
    stack<int> st;
    string s, ex;
    getline(cin, s);
    stringstream str(s);
    while (str >> ex) {
        if (!(ex == "-" || ex == "+" || ex == "*" || ex == "/")) st.push(atoi(exp.c_str()));
        else {
            if (!st.empty()) {
                b = st.top();
                st.pop();
            } else {
                flag = true;
                break;
            }
            if (!st.empty()) {
                a = st.top();
                st.pop();
            } else {
                flag = true;
                break;
            }
            switch (ex[0]) {
            case '+':
                st.push(a + b);
                break;
            case '-':
                st.push(a - b);
                break;
            case '*':
                st.push(a * b);
                break;
            case '/':
                if (b != 0) st.push(a / b);
                else {
                    cout << "ERROR\n";
                    return 0;
                }
                break;
            }
        }
    }
    if (!st.empty() && !flag) {
        int c = st.top();
        st.pop();
        if (st.empty()) {
            cout << c << "\n";
        } else {
            cout << "ERROR\n";
        }
    } else {
        cout << "ERROR\n";
    }
    system("pause");
    return 0;
}
Ссылка на задачу: https://informatics.msk.ru/mod... rid=112494
0
IT_Exp
Эксперт
34794 / 4073 / 2104
Регистрация: 17.06.2006
Сообщений: 32,602
Блог
07.07.2018, 15:46
Ответы с готовыми решениями:

Обратная польская запись (ОПЗ)
Пожалуйста помогите!!!! не знаю что мне сделать с этими задачами=((((( A. Обратная польская запись (ОПЗ). Постфиксной формой записи...

Обратная польская запись
Доброго времени суток. Нужно сделать программу которая переводит арифм. выражение в обратную польскую запись и считает его по ней. ...

Обратная польская запись
Пожалуйста помогите, всю голову себе сломал. Задание: &quot;Обеспечить перевод инфиксного выражения в ОПЗ и вычислить его результат. Входные...

38
 Аватар для QuakerRUS
1469 / 1010 / 456
Регистрация: 30.10.2017
Сообщений: 2,799
07.07.2018, 19:46
Студворк — интернет-сервис помощи студентам
IGPIGP, 2 2 2 * + крашит программу.
0
 Аватар для Fixer_84
1505 / 969 / 812
Регистрация: 30.04.2016
Сообщений: 3,337
07.07.2018, 19:50  [ТС]
Цитата Сообщение от Fixer_84 Посмотреть сообщение
P.S. Сейчас попробую отправить ваш новый код...
К сожалению, ничего не изменилось.
0
Комп_Оратор)
Эксперт по математике/физике
 Аватар для IGPIGP
9007 / 4708 / 630
Регистрация: 04.12.2011
Сообщений: 14,003
Записей в блоге: 16
07.07.2018, 19:50
Цитата Сообщение от QuakerRUS Посмотреть сообщение
IGPIGP, 2 2 2 * + крашит программу.
Естественно. Ввод операнда должен чередоваться вводом операции. Иначе логика будет странной. То есть, Вы имеете ввиду, что можно ввести десяток чисел, а потом операцию которая будет групповой для данной десятки?
0
 Аватар для QuakerRUS
1469 / 1010 / 456
Регистрация: 30.10.2017
Сообщений: 2,799
07.07.2018, 19:53
Fixer_84, а есть те, кто успешно эту задачу сдал? Именно на этом ресурсе, на более солидных нормальные условия как правило и как минимум указаны входные параметры.

Добавлено через 2 минуты
IGPIGP, что естественно, то еще не значит правильно. Для ознакомления.
https://ru.wikipedia.org/wiki/... кая_запись
0
 Аватар для Fixer_84
1505 / 969 / 812
Регистрация: 30.04.2016
Сообщений: 3,337
07.07.2018, 19:57  [ТС]
Цитата Сообщение от QuakerRUS Посмотреть сообщение
а есть те, кто успешно эту задачу сдал?
Есть, но мало. Однако их коды не публикуются.
0
 Аватар для QuakerRUS
1469 / 1010 / 456
Регистрация: 30.10.2017
Сообщений: 2,799
07.07.2018, 20:00
Fixer_84, а так если?

C++
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
#include <iostream>
#include <string>
#include <sstream>
#include <stack>
#include <cctype>
 
using namespace std;
 
bool error = false;
unsigned int evaluatePostfixExpression(const string&);
unsigned int calculate(unsigned int, unsigned int, char);
 
int main() {
    string postfix;
    unsigned int result;
    getline(cin, postfix);
 
    if (postfix.size() == 0 || isspace(postfix[0]) || isspace(postfix[postfix.size() - 1]))
        error = true;
 
    for (int i = 1; i < postfix.size(); ++i)
    {
        if (isspace(postfix[i]) && postfix[i] != ' ' || postfix[i - 1] == ' ' && postfix[i] == ' ')
            error = true;
    }
 
    if (!error)
        result = evaluatePostfixExpression(postfix);
 
    if (!error)
        cout << result << "\n";
    else
        cout << "ERROR\n";
    system("pause");
    return 0;
}
 
unsigned int evaluatePostfixExpression(const string& st) {
    stack<unsigned int> stack;
    istringstream postfix(st);
    unsigned int x, y, n, r;
    string s;
 
    while (postfix >> s)
    {
        if (s == "+" || s == "-" || s == "*" || s == "/")
        {
            if (stack.empty())
            {
                error = true;
                return 0;
            }
 
            x = stack.top();
            stack.pop();
 
            if (stack.empty())
            {
                error = true;
                return 0;
            }
 
            y = stack.top();
            stack.pop();
            stack.push(calculate(y, x, s[0]));
        }
        else
        {
            if (s[0] != '-' && s[0] != '+' && !isdigit(s[0]))
            {
                error = true;
                return 0;
            }
 
            for (int i = 1; i < s.size(); ++i)
            {
                if (!isdigit(s[i]))
                {
                    error = true;
                    return 0;
                }
            }
 
            istringstream ss(s);
            ss >> n;
            stack.push(n);
        }
    }
 
    if (stack.empty())
    {
        error = true;
        return 0;
    }
 
    r = stack.top();
    stack.pop();
 
    if (!stack.empty())
        error = true;
 
    return r;
}
 
unsigned int calculate(unsigned int op1, unsigned int op2, char operat) {
    unsigned int result;
 
    switch (operat) {
    case '+':
        result = op1 + op2;
        break;
    case '-':
        result = op1 - op2;
        break;
    case '*':
        result = op1 * op2;
        break;
    case '/':
        if (op2 != 0)
            result = op1 / op2;
        else {
            result = 0;
            error = true;
        }
        break;
    }
    return result;
}
0
Комп_Оратор)
Эксперт по математике/физике
 Аватар для IGPIGP
9007 / 4708 / 630
Регистрация: 04.12.2011
Сообщений: 14,003
Записей в блоге: 16
07.07.2018, 20:02
Цитата Сообщение от QuakerRUS Посмотреть сообщение
что естественно, то еще не значит правильно.
Это верно. Но то что неестестественно всегда непраильно. Невозможность использования унарных операторов, это само по себе инвалидно, а вот невозможность ввода чисел в формате 1.234e-5, это совсем деревянная игрушка. Впрочем, задание есть задание. Оно выполнимо, конечно.
0
 Аватар для QuakerRUS
1469 / 1010 / 456
Регистрация: 30.10.2017
Сообщений: 2,799
07.07.2018, 20:10
Цитата Сообщение от IGPIGP Посмотреть сообщение
Невозможность использования унарных операторов, это само по себе инвалидно
В моем коде можно использовать унарные + и -.

Цитата Сообщение от IGPIGP Посмотреть сообщение
а вот невозможность ввода чисел в формате 1.234e-5, это совсем деревянная игрушка
В условии написано о целых числах, а не с плавающей точкой. Хотя криворукость тех, кто "тырил" задачи с известных сайтов и адаптировал криво под свой может привести к чему угодно, и можно только удивляться и разводить руками.
0
 Аватар для Fixer_84
1505 / 969 / 812
Регистрация: 30.04.2016
Сообщений: 3,337
07.07.2018, 20:23  [ТС]
Цитата Сообщение от QuakerRUS Посмотреть сообщение
Fixer_84, а так если?
А так в 7 тестах - неправильный ответ.
0
 Аватар для QuakerRUS
1469 / 1010 / 456
Регистрация: 30.10.2017
Сообщений: 2,799
07.07.2018, 20:28
Fixer_84, так, значит все же они используют в тестах отрицательные числа.

Добавлено через 4 минуты
Fixer_84, в порядке эксперимента добавил возможность записывать числа в формате xe+y

C++
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
#include <iostream>
#include <string>
#include <sstream>
#include <stack>
#include <cctype>
 
using namespace std;
 
bool error = false;
long long evaluatePostfixExpression(const string&);
long long calculate(long long, long long, char);
 
int main() {
    string postfix;
    long long result;
    getline(cin, postfix);
 
    result = evaluatePostfixExpression(postfix);
 
    if (!error)
        cout << result << "\n";
    else
        cout << "ERROR\n";
    system("pause");
    return 0;
}
 
long long evaluatePostfixExpression(const string& st) {
    stack<long long> stack;
    istringstream postfix(st);
    long long x, y, n, r;
    double d;
    string s;
 
    while (postfix >> s)
    {
        if (s == "+" || s == "-" || s == "*" || s == "/")
        {
            if (stack.empty())
            {
                error = true;
                return 0;
            }
 
            x = stack.top();
            stack.pop();
 
            if (stack.empty())
            {
                error = true;
                return 0;
            }
 
            y = stack.top();
            stack.pop();
            stack.push(calculate(y, x, s[0]));
        }
        else
        {
            istringstream ss(s);
            ss >> d;
            n = d;
            stack.push(n);
        }
    }
 
    if (stack.empty())
    {
        error = true;
        return 0;
    }
 
    r = stack.top();
    stack.pop();
 
    if (!stack.empty())
        error = true;
 
    return r;
}
 
long long calculate(long long op1, long long op2, char operat) {
    long long result;
 
    switch (operat) {
    case '+':
        result = op1 + op2;
        break;
    case '-':
        result = op1 - op2;
        break;
    case '*':
        result = op1 * op2;
        break;
    case '/':
        if (op2 != 0)
            result = op1 / op2;
        else {
            result = 0;
            error = true;
        }
        break;
    }
    return result;
}
0
 Аватар для Fixer_84
1505 / 969 / 812
Регистрация: 30.04.2016
Сообщений: 3,337
07.07.2018, 20:39  [ТС]
Цитата Сообщение от QuakerRUS Посмотреть сообщение
Fixer_84, в порядке эксперимента добавил возможность записывать числа в формате xe+y
В тех же двух тестах - неправильный ответ.
0
 Аватар для QuakerRUS
1469 / 1010 / 456
Регистрация: 30.10.2017
Сообщений: 2,799
07.07.2018, 20:41
Fixer_84, значит идея IGPIGP не прокатила. Пока больше нет мыслей что за данные они пытаются подавать.
0
 Аватар для Fixer_84
1505 / 969 / 812
Регистрация: 30.04.2016
Сообщений: 3,337
07.07.2018, 20:42  [ТС]
QuakerRUS, я сейчас напишу им письмо в telegram. Возможно, там ответят. Кто-то эту задачу скорее всего сдавал.
0
 Аватар для QuakerRUS
1469 / 1010 / 456
Регистрация: 30.10.2017
Сообщений: 2,799
07.07.2018, 20:44
Fixer_84, кстати, а на е-олимпе условие такое же? Может оттуда можно больше почерпнуть?
0
 Аватар для Fixer_84
1505 / 969 / 812
Регистрация: 30.04.2016
Сообщений: 3,337
07.07.2018, 20:48  [ТС]
QuakerRUS, там такое же условие, но нет проверки на вывод сообщения ERROR. Там решение из поста #1 проходит все тесты и ваше тоже проходит, скорее всего, но я не отправлял. Лично я считаю, что вывод сообщения об ошибке тут очень нужен для тех, кто например, калькулятор собрался делать
0
 Аватар для QuakerRUS
1469 / 1010 / 456
Регистрация: 30.10.2017
Сообщений: 2,799
07.07.2018, 21:06
Fixer_84, сообщения об ошибках я тоже учел во всех мыслимых и немыслимых случаях. Не факт, что у них вообще корректно проверяются результаты.
0
 Аватар для Fixer_84
1505 / 969 / 812
Регистрация: 30.04.2016
Сообщений: 3,337
07.07.2018, 21:56  [ТС]
Цитата Сообщение от QuakerRUS Посмотреть сообщение
Fixer_84, сообщения об ошибках я тоже учел во всех мыслимых и немыслимых случаях. Не факт, что у них вообще корректно проверяются результаты.
Возможно. Сейчас пытаюсь выяснить, что может быть не так через telegram. У них там служба поддержки.
0
Комп_Оратор)
Эксперт по математике/физике
 Аватар для IGPIGP
9007 / 4708 / 630
Регистрация: 04.12.2011
Сообщений: 14,003
Записей в блоге: 16
07.07.2018, 22:17
Цитата Сообщение от QuakerRUS Посмотреть сообщение
В моем коде можно использовать унарные + и -.
а как же
Цитата Сообщение от QuakerRUS Посмотреть сообщение
что естественно, то еще не значит правильно. Для ознакомления.
там по ссылке:
Цитата Сообщение от wiki
В отличие от инфиксной записи, невозможно использовать одни и те же знаки для записи унарных и бинарных операций. Так, в инфиксной записи выражение 5 * (−3 + 8) использует знак «минус» как символ унарной операции (изменение знака числа), а выражение (10 − 15) * 3 применяет этот же знак для обозначения бинарной операции (вычитание).
То есть, все мы тут поляки, по своему.
Меня удручает сама идея калькулькулятора с двумя раздельными конвеерами - конвеер данных и конвеер команд. Тяжеловато будет пользоваться (имхо). Хотя для вычислительной системы есть профит в, по крайней мере, разделении фораматов для данных и для команд. Но тогда уж знак '-' в записи "-123" не должен повторяться в команде "minus". Может это и имеет смысл, но я его не вижу. Для стековых и рекурсивных алгоритмов можно найти задачи в которых абстракция не деоётся с здравым смыслом логикой предметной области.
0
 Аватар для QuakerRUS
1469 / 1010 / 456
Регистрация: 30.10.2017
Сообщений: 2,799
07.07.2018, 22:23
IGPIGP, да я сначала без унарных делал, потом сделал с унарными. Чего только не перепробовал, чтобы пробить эти два возможных варианта.
0
Надоела реклама? Зарегистрируйтесь и она исчезнет полностью.
BasicMan
Эксперт
29316 / 5623 / 2384
Регистрация: 17.02.2009
Сообщений: 30,364
Блог
07.07.2018, 22:23

Обратная польская запись
Нужно создать класс с++ для вычисления обратной польской записи с помощь стека.

Обратная польская запись
Написать программу формирования ОПЗ и расчета полученного вы-ражения. Разработать удобный интерфейс ввода исходных данных и вывода...

Обратная Польская Запись
Сам вопрос: Я написал программу, она работает, но препод по Структурам данных сломал ее в два счета. Я нашел ошибку, но как ее исправить...

Обратная польская запись
Нужна помощь. Есть программа с общей польской записью. Программа принимает только буквенное выражение ( например: &quot;a+b+c*d&quot; и...

Обратная польская запись
Что такое обратная польская запись и как её реализовать на С++? Почему когда в программе я пишу a=2+2; всё считает нормально, а когда пишу...


Искать еще темы с ответами

Или воспользуйтесь поиском по форуму:
39
Ответ Создать тему
Новые блоги и статьи
интеграция AnyLogic с самописным REST API и переход на Odoo
anaschu 03.07.2026
Успешная интеграция AnyLogic с самописным REST API и переход на промышленную Odoo WMS Сегодня проделал огромный путь от простой симуляции физических процессов до построения полноценной. . .
Поиск всех путей на ориентированном графе. Linux
dcc0 02.07.2026
Переработка старого кода из моей статьи. Через несколько переработок от PHP кода к C89 (надеюсь, 89). Но довольно запутанно получилось. Код для Linux. Но если убрать time и то, что с ним. . .
Сам себя обучал rest api
anaschu 02.07.2026
Педагогический лайфхак: Почему чистый REST API для ученика намного круче, чем готовые библиотеки Когда мы отказались от капризного JAR-файла AnyLogic и переписали код на стандартный HttpClient,. . .
rest api anylogic - выполнение модели на своём русском сайте
anaschu 02.07.2026
Как подружиться с AnyLogic Cloud API, победить провайдеров и развернуться Java-бэкенд в Docker на бесплатном хостинге: Двухдневный лог борьбы Всем привет! Хочу поделиться свежим (и довольно. . .
Где деньги лежат
kumehtar 02.07.2026
Это - японская подводная лодка I-52 (тип C2, кодовое имя Momi) вышла из Японии в марте 1944 года с миссией в оккупированную немцами Францию (Лорьян). Это была одна из «Янаги»-миссий по обмену. . .
Krabik для WoW 3.3.5a, многоязычный
AmbA 02.07.2026
Допилил бота, думаю что окончательно. Изменения: - добавлена многоязычность - добавлено снятие скриншотов - добавлено поддержание бафов хождения по воде (для жреца, дк и шамана) - и так, по. . .
Алиса нашла кучу ошибок компиляции и запуска в проекте, который без проблем компилировался и запускался)))
anaschu 30.06.2026
Я пока посмеюся, но завтра проверю. А вообще интерсно. Дал алисе файл, в котором точно нет ошибок компиляции и запуска, и попросил их найти. Нашла кучу))) Критические ошибки, мешающие компиляции и. . .
сукцессия 16. Общий обзор, в основном что бы другие ии поняли
anaschu 29.06.2026
# Передаточный документ: модель микоризной сукцессии (для нового чата) Этот документ предназначен для того, чтобы новый чат Claude мог продолжить работу без необходимости заново разбираться в. . .
КиберФорум - форум программистов, компьютерный форум, программирование
Powered by vBulletin
Copyright ©2000 - 2026, CyberForum.ru