Форум программистов, компьютерный форум, киберфорум
Наши страницы

С++ для начинающих

Войти
Регистрация
Восстановить пароль
 
 
Рейтинг: Рейтинг темы: голосов - 10, средняя оценка - 4.60
maxon887
12 / 12 / 3
Регистрация: 05.06.2012
Сообщений: 280
#1

Калькулятор страуструпа - C++

20.09.2013, 12:29. Просмотров 1430. Ответов 15
Метки нет (Все метки)

Ну по крайней мере если это и не он, то очень на него похож.
Проблема в скобках.Например:
(1+1 - всё хорошо, выплывет ощибка "Expected right bracket"
1+1) - плохо, каклькуляторо продолжит работать, для больших выражений результат не предсказуемый.
Надо это как то починить, я уже сам голову сламал))) Спасибо зарание.
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
#include <iostream>
using namespace std;
enum TokenValue
{
    END,NUMBER,PLUS='+',MINUS='-',MUL='*',DIV='/',
    LB='(',RB=')'
};
TokenValue CurrentSymbol;
double CurrentNumber;
int errors;
 
double error(const char* s)
{
    cerr<<"Error: "<<s<<endl;
    errors++;
    return -1;
}
 
double expr();
TokenValue GetSymbol()
{
    char ch=0;
    ch=cin.get();
    switch(ch)
    {
    case'\n':
        return CurrentSymbol=END;
    case'1': case'2': case'3': case'4': case'5':
    case'6': case'7': case'8': case'9': case'0':
        cin.putback(ch);
        cin>>CurrentNumber;
        return CurrentSymbol=NUMBER;
    case'+': case'-': case'*': case'/':
    case'(': case')':
        return CurrentSymbol=TokenValue(ch);
    default:
        error("Imput error");
        return CurrentSymbol=END;
    }
}
 
double prim()
{
    switch(CurrentSymbol)
    {
    case NUMBER:
        GetSymbol();
        return CurrentNumber;
    case LB:
    {
        GetSymbol();
        double e=expr();
        if(CurrentSymbol!=RB)
            return error("Expected right bracket");
        GetSymbol();
        return e;
    }
    default:
        error("Primary expected");
        GetSymbol();
        return -1;
    }
}
 
double term()
{
    double left=prim();
    while(1)
    {
        switch(CurrentSymbol)
        {
        case MUL:
            GetSymbol();
            left *=prim();
            break;
        case DIV:
        {
            GetSymbol();
            double d=prim();
            if(d!=0)
                left /= d;
            else
                error("Division by zero");
            break;
        }
        default:
            return left;
        }
    }
}
 
double expr()
{
    double left=term();
    while(1)
    {
        switch(CurrentSymbol)
        {
        case PLUS:
            GetSymbol();
            left += term();
            break;
        case MINUS:
            GetSymbol();
            left -= term();
            break;
        default:
            return left;
        }
    }
}
 
int main()
{
    while(1)
    {
        GetSymbol();
        if(CurrentSymbol==END)
            continue;
        cout<<expr()<<endl;
    }
    return 0;
}
0
Надоела реклама? Зарегистрируйтесь и она исчезнет полностью.
Similar
Эксперт
41792 / 34177 / 6122
Регистрация: 12.04.2006
Сообщений: 57,940
20.09.2013, 12:29
Здравствуйте! Я подобрал для вас темы с ответами на вопрос Калькулятор страуструпа (C++):

Калькулятор Страуструпа (C++) - C++
Добрый вечер! Я изучаю &quot;Принципы и практика использования C++&quot; Страуструпа. Все, что он пишет, хорошо понимаю, но следующая логика...

Калькулятор Страуструпа С++ - C++
Я новичок в С++, пытаюсь читать Страуструпа. Дошёл до строчного калькулятора и не понимаю принципов его работы, перечитывал главу 4 раза....

Калькулятор в книге Страуструпа - C++
Приветствую всех кто читает эту тему. У меня возникла проблема во время написании калькулятора. Он был описан в 6 главе книги и там же...

Калькулятор в книге Страуструпа - C++
Я знал, что это довольно тяжелая книга, поэтому начал читать ее после другой о С++, но пример &quot;элементарного&quot; калькулятора поставил меня в...

Упражнение из книги Страуструпа. Программа мини-калькулятор. Цифры записанные в строковом формате - C++
Привет всем. Не могу понять, как необходимо изменить программу исходя из условия упражнения. Упражнение сформулировано так: ...

Задание из Страуструпа - C++
Добрый день,дорогие форумчане.В общем читаю книжечку Страуструпа.Выполняю задания.Вот что-то у меня ступор.Прошу Вашего совета:) ...

15
Cynacyn
33 / 33 / 0
Регистрация: 02.05.2013
Сообщений: 109
20.09.2013, 13:00 #2
Помню сам долго парился с тем, чтобы добавить обработку скобок. Я запомнил что очень важно правильно определить грамматику.
Под спойлером Вы можете увидеть как это сделал я:
Кликните здесь для просмотра всего текста
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
// Calculator.h
/*
 
    Grammatis:
 
        calculation:
            statement
            print
            quit
            calculation statement
        statement:
            declaration
            expression
        declaration:
            "let" name "=" expression
        print:
            ';'
        quit:
            'q'
 
        expression:
            term
            expression '+' term
            expression '-' term
        term:
            primary
            term '*' primary
            term '/' primary
        primary:
            number
            name
            number name
            '('expression')'
            '-' primary
            '+' primary
            sqrt primary
            pow '(' expression ',' expression ')'
            name '=' expression
            help
        number:
            floating_point_literal
        name:
            string_literal
        help:
            help
            
 
 
 
*/


Пример моей реализации калькулятора (буду рад отзывам):

http://codepad.org/OcGLe0Pd
http://codepad.org/RFm9DKzb

пример использования:
C++
1
2
3
int main() { 
calculate(std::cin,std::cout); 
return 0;
1
Nullik
43 / 12 / 1
Регистрация: 13.03.2013
Сообщений: 300
Завершенные тесты: 1
20.09.2013, 13:02 #3
это чем-то похоже на обратную польскую запись через стек?
0
Cynacyn
33 / 33 / 0
Регистрация: 02.05.2013
Сообщений: 109
20.09.2013, 13:07 #4
Цитата Сообщение от Nullik Посмотреть сообщение
это чем-то похоже на обратную польскую запись через стек?
Глянул в вики что есть ОПЗ - здесь определяется естественная грамматика для работы с потоком символов, не знаю в чем может быть сходство.

Т.е. можно написать (2+2)2, ответ = 8.

P.S. Исправил ссылки.

Calculator.h
Calculator.cpp
0
Nullik
43 / 12 / 1
Регистрация: 13.03.2013
Сообщений: 300
Завершенные тесты: 1
20.09.2013, 13:24 #5
Cynacyn, не могу найти в инете: а этот калькулятор что делает? Примеры, если не трудно.

Ну, польская так: 2+2*(8-1)
Кликните здесь для просмотра всего текста

1) стек1:
2
стек2:

2)
стек1:
2
стек2:
+

3)
стек1:
2
2
стек2:
+

4)
стек1:
2
2
стек2:
+
*

5)
стек1:
2
2
стек2:
+
*
(

6)
стек1:
2
2
8
стек2:
+
*
(

7)
стек1:
2
2
8
стек2:
+
*
(
-

8)
стек1:
2
2
8
1
стек2:
+
*
(
-

9) (встретили закрывающую скобку, пошли до первой открывающей)
стек1:
2
2
7 (сделали действия, пока шли обратно)
стек2:
+
*

10) т.к. конец строки, то начинаем из стеков доставать:
стек1:
2
14 (сделали действия, пока шли обратно)
стек2:
+

11)
стек1:
16
стек2:
0
Cynacyn
33 / 33 / 0
Регистрация: 02.05.2013
Сообщений: 109
20.09.2013, 13:30 #6
Цитата Сообщение от Nullik Посмотреть сообщение
Cynacyn, не могу найти в инете: а этот калькулятор что делает? Примеры, если не трудно.

Ну, польская так: 2+2*(8-1)
Кликните здесь для просмотра всего текста



обычные арифметические действия, используя обычные приоритет арифметических операторов и скобок, позволяет объявлять переменные, считает корень/степень, уже не помню что ещё - скомрилируйте программу используя cin, cout как аргументы calculate и введите help
1
maxon887
12 / 12 / 3
Регистрация: 05.06.2012
Сообщений: 280
20.09.2013, 13:46  [ТС] #7
Цитата Сообщение от Cynacyn Посмотреть сообщение
Пример моей реализации калькулятора (буду рад отзывам):
Не собрался в виду отсутствия std_lib_facilities.h
0
Cynacyn
33 / 33 / 0
Регистрация: 02.05.2013
Сообщений: 109
20.09.2013, 13:48 #8
Цитата Сообщение от maxon887 Посмотреть сообщение
Не собрался в виду отсутствия std_lib_facilities.h
std_lib_facilities.h переименуйте в std_lib_facilities.h и сохраните в директорию проекта (туда где лежит файл содержащий main())
Вот ссылка на страницу с кодом :std_lib_facilities.h
1
maxon887
12 / 12 / 3
Регистрация: 05.06.2012
Сообщений: 280
20.09.2013, 23:12  [ТС] #9
да блин вы видели как он вообще функцию поиска из таблицы имён реализовал???
это вообще что такое?))
C++
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
name* look(const char* p, int ins =0)
{
int ii = 0; // хэш-код
const char* pp = p;
while (*pp) ii = ii<<1 ^ *pp++;
if (ii < 0) ii = -ii;
ii %= TBLSZ;
for (name* n=table[ii]; n; n=n->next) // поиск
if (strcmp(p,n->string) == 0) return n;
if (ins == 0) error("имя не найдено");
name* nn = new name; // занесение
nn->string = new char[strlen(p)+1];
strcpy(nn->string,p);
nn->value = 1;
nn->next = table[ii];
table[ii] = nn;
return nn;
}
0
Cynacyn
33 / 33 / 0
Регистрация: 02.05.2013
Сообщений: 109
23.09.2013, 09:34 #10
Цитата Сообщение от maxon887 Посмотреть сообщение
да блин вы видели как он вообще функцию поиска из таблицы имён реализовал???
это вообще что такое?))
C++
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
name* look(const char* p, int ins =0)
{
int ii = 0; // хэш-код
const char* pp = p;
while (*pp) ii = ii<<1 ^ *pp++;
if (ii < 0) ii = -ii;
ii %= TBLSZ;
for (name* n=table[ii]; n; n=n->next) // поиск
if (strcmp(p,n->string) == 0) return n;
if (ins == 0) error("имя не найдено");
name* nn = new name; // занесение
nn->string = new char[strlen(p)+1];
strcpy(nn->string,p);
nn->value = 1;
nn->next = table[ii];
table[ii] = nn;
return nn;
}
кто "он"?
0
maxon887
12 / 12 / 3
Регистрация: 05.06.2012
Сообщений: 280
23.09.2013, 11:43  [ТС] #11
страуструп
0
Cynacyn
33 / 33 / 0
Регистрация: 02.05.2013
Сообщений: 109
23.09.2013, 11:44 #12
Цитата Сообщение от maxon887 Посмотреть сообщение
страуструп
а откуда у Вас этот код?
0
maxon887
12 / 12 / 3
Регистрация: 05.06.2012
Сообщений: 280
23.09.2013, 14:18  [ТС] #13
http://rutracker.org/forum/viewtopic.php?t=2226992
страница 77
0
Cynacyn
33 / 33 / 0
Регистрация: 02.05.2013
Сообщений: 109
23.09.2013, 17:05 #14
Цитата Сообщение от maxon887 Посмотреть сообщение
Я ещё не работал с этой книгой, пока только "Принципы и практику использования С++" изучаю. Там такого нет.
0
maxon887
12 / 12 / 3
Регистрация: 05.06.2012
Сообщений: 280
23.09.2013, 18:34  [ТС] #15
а можно ссылку?
0
23.09.2013, 18:34
MoreAnswers
Эксперт
37091 / 29110 / 5898
Регистрация: 17.06.2006
Сообщений: 43,301
23.09.2013, 18:34
Привет! Вот еще темы с ответами:

Угадайка от Страуструпа - C++
Писал, писал, устал. В логике ошибок нет. Как алгоритм оптимизировать и спагетти свернуть? #include &quot;std_lib_facilities.h&quot; int...

задачки Страуструпа - C++
Сижу в обнимку с талмудом Страуструпа, изучаю С++ самостоятельно. Просить код писать не буду, разберусь. Некоторые терминологические вещи...

Задача из книги Страуструпа - C++
Меня настораживает несколько странная формулировка, я не понимаю зачем так предлагают решать задачу: Напишите программу, содержащую цикл...

Тайна Страуструпа - std_lib_facilities.h (2) - C++
Ребят уже голову сломал как дописать в код. Предложите пользователю ввести значение m если ваш друг -мужчина, f -если женщина. ...


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

Или воспользуйтесь поиском по форуму:
15
Ответ Создать тему
Опции темы

КиберФорум - форум программистов, компьютерный форум, программирование
Powered by vBulletin® Version 3.8.9
Copyright ©2000 - 2017, vBulletin Solutions, Inc.