Язык программирования C++ для профессионалов


Анализатор - часть 3


double expr(); // это описание необходимо

Функция term() справляется с умножением и делением аналогично тому, как функция expr() со сложением и вычитанием:

double term() // умножает и делит { double left = prim();

for(;;) switch(curr_tok) { case MUL: get_token(); // случай '*' left *= prim(); break; case DIV: get_token(); // случай '/' double d = prim(); if (d == 0) return error("деление на 0"); left /= d; break; default: return left; } }

Проверка отсутствия деления на нуль необходима, поскольку результат деления на нуль неопределен и, как правило, приводит к катастрофе.

Функция error() будет рассмотрена позже. Переменная d появляется в программе там, где она действительно нужна, и сразу же инициализируется. Во многих языках описание может находиться только в начале блока. Но такое ограничение может искажать естественную структуру программы и способствовать появлению ошибок. Чаще всего не инициализированные локальные переменные свидетельствуют о плохом стиле программирования. Исключение составляют те переменные, которые инициализируются операторами ввода, и переменные типа массива или структуры, для которых нет традиционной инициализации с помощью одиночных присваиваний. Следует напомнить, что = является операцией присваивания, тогда как == есть операция сравнения.

Функция prim, обрабатывающая первичное, во многом похожа на функции expr и term(). Но раз мы дошли до низа в иерархии вызовов, то в ней кое-что придется сделать. Цикл для нее не нужен:

double number_value; char name_string[256];

double prim() // обрабатывает первичное { switch (curr_tok) { case NUMBER: // константа с плавающей точкой get_token(); return number_value; case NAME: if (get_token() == ASSIGN) { name* n = insert(name_string); get_token(); n->value = expr(); return n->value; } return look(name_string)->value; case MINUS: // унарный минус get_token(); return -prim(); case LP: get_token(); double e = expr(); if (curr_tok != RP) return error("требуется )"); get_token(); return e; case END: return 1; default: return error("требуется первичное"); } }




Начало  Назад  Вперед



Книжный магазин