Π§ΠΈΡ‚Π°ΠΉΡ‚Π΅ ΠΊΠ½ΠΈΠ³ΠΈ ΠΎΠ½Π»Π°ΠΉΠ½ Π½Π° Bookidrom.ru! БСсплатныС ΠΊΠ½ΠΈΠ³ΠΈ Π² ΠΎΠ΄Π½ΠΎΠΌ ΠΊΠ»ΠΈΠΊΠ΅

Π§ΠΈΡ‚Π°Ρ‚ΡŒ ΠΎΠ½Π»Π°ΠΉΠ½ Β«C++Β». Π‘Ρ‚Ρ€Π°Π½ΠΈΡ†Π° 27

Автор Бтраустрап Π‘ΡŒΡΡ€Π½

// dc.h: ΠΎΠ±Ρ‰ΠΈΠ΅ описания для ΠΊΠ°Π»ΡŒΠΊΡƒΠ»ΡΡ‚ΠΎΡ€Π°

enum token_value (* NAME, NUMBER, END, PLUS='+', MINUS='-', MUL='*', DIV='/', PRINT=';', ASSIGN='=', LP='(', RP=')' *);

extern int no_of_errors; extern double error(char* s); extern token_value get_token(); extern token_value curr_tok; extern double number_value; extern char name_string[256];

extern double expr(); extern double term(); extern double prim();

struct name (* char* string; name* next; double value; *);

extern name* look(char* p, int ins = 0); inline name* insert(char* s) (* return look(s,1); *)

Если ΠΎΠΏΡƒΡΡ‚ΠΈΡ‚ΡŒ фактичСский ΠΊΠΎΠ΄, Ρ‚ΠΎ lex.c Π±ΡƒΠ΄Π΅Ρ‚ Π²Ρ‹Π³Π»ΡΠ΄Π΅Ρ‚ΡŒ ΠΏΡ€ΠΈΠΌΠ΅Ρ€Π½ΠΎ Ρ‚Π°ΠΊ:

// lex.c: Π²Π²ΠΎΠ΄ ΠΈ лСксичСский Π°Π½Π°Π»ΠΈΠ· #include Β«dc.hΒ»

#include Β«ctype.hΒ»

token_value curr_tok; double number_value; char name_string[256];

token_value get_token() (* /* ... */ *)

Π—Π°ΠΌΠ΅Ρ‚ΡŒΡ‚Π΅, Ρ‡Ρ‚ΠΎ Ρ‚Π°ΠΊΠΎΠ΅ использованиС Π·Π°Π³ΠΎΠ»ΠΎΠ²ΠΎΡ‡Π½Ρ‹Ρ… Ρ„Π°ΠΉΠ»ΠΎΠ² Π³Π°Ρ€Π°Π½Ρ‚ΠΈΡ€ΡƒΠ΅Ρ‚, Ρ‡Ρ‚ΠΎ ΠΊΠ°ΠΆΠ΄ΠΎΠ΅ описаниС Π² Π·Π°Π³ΠΎΠ»ΠΎΠ²ΠΎΡ‡Π½ΠΎΠΌ Ρ„Π°ΠΉΠ»Π΅ ΠΎΠ±ΡŠΠ΅Ρ‚Π°, ΠΎΠΏΡ€Π΅Π΄Π΅Π»Π΅Π½Π½ΠΎΠ³ΠΎ ΠΏΠΎΠ»ΡŒΠ·ΠΎΠ²Π°Ρ‚Π΅Π»Π΅ΠΌ, Π±ΡƒΠ΄Π΅Ρ‚ Π² ΠΊΠ°ΠΊΠΎΠΉ-Ρ‚ΠΎ ΠΌΠΎΠΌΠ΅Π½Ρ‚ Π²ΠΊΠ»ΡŽΡ‡Π΅Π½ΠΎ Π² Ρ„Π°ΠΉΠ», Π³Π΄Π΅ ΠΎΠ½ опрСдСляСтся. НапримСр, ΠΏΡ€ΠΈ ΠΊΠΎΠΌΠΏΠΈΠ»Ρ†ΠΈΠΈ lex.c компилятору Π±ΡƒΠ΄Π΅Ρ‚ ΠΏΠ΅Ρ€Π΅Π΄Π°Π½ΠΎ:

extern token_value get_token(); // ... token_value get_token() (* /* ... */ *)

Π­Ρ‚ΠΎ обСспСчиваСт Ρ‚ΠΎ, Ρ‡Ρ‚ΠΎ компилятор ΠΎΠ±Π½Π°Ρ€ΡƒΠΆΠΈΡ‚ Π»ΡŽΠ±ΡƒΡŽ Π½ΡΠΎΠ³Π»Π°ΡΠΎΠ²Π°Π½Π½ΠΎΡΡ‚ΡŒ Π² Ρ‚ΠΈΠΏΠ°Ρ…, ΡƒΠΊΠ°Π·Π°Π½Π½Ρ‹Ρ… для ΠΈΠΌΠ΅Π½ΠΈ. НапримСр, Ссли Π±Ρ‹ get_token() Π±Ρ‹Π»Π° описана ΠΊΠ°ΠΊ Π²ΠΎΠ·Π²Ρ€Π°Ρ‰Π°ΡŽΡ‰Π°Ρ token_value, Π½ΠΎ ΠΏΡ€ΠΈ этом ΠΎΠΏΡ€Π΅Π΄Π΅Π»Π΅Π½Π° ΠΊΠ°ΠΊ Π²ΠΎΠ·Π²Ρ€Π°Ρ‰Π°ΡŽΡ‰Π°Ρ int, компиляция lex.c Π½Π΅ ΠΏΡ€ΠΎΡˆΠ»Π° Π±Ρ‹ ΠΈΠ·Π·Π° ошибки нСсоотвСтствия Ρ‚ΠΈΠΏΠΎΠ².

Π€Π°ΠΉΠ» syn.c Π±ΡƒΠ΄Π΅Ρ‚ Π²Ρ‹Π³Π»ΡΠ΄Π΅Ρ‚ΡŒ ΠΏΡ€ΠΈΠΌΠ΅Ρ€Π½ΠΎ Ρ‚Π°ΠΊ:

// syn.c: синтаксичСский Π°Π½Π°Π»ΠΈΠ· ΠΈ вычислСниС

#include Β«dc.hΒ»

double prim() (* /* ... */ *) double term() (* /* ... */ *) double expr() (* /* ... */ *)

Π€Π°ΠΉΠ» table.c Π±ΡƒΠ΄Π΅Ρ‚ Π²Ρ‹Π³Π»ΡΠ΄Π΅Ρ‚ΡŒ ΠΏΡ€ΠΈΠΌΠ΅Ρ€Π½ΠΎ Ρ‚Π°ΠΊ:

// table.c: Ρ‚Π°Π±Π»ΠΈΡ†Π° ΠΈΠΌΠ΅Π½ ΠΈ просмотр

#include Β«dc.hΒ»

extern char* strcmp(const char*, const char*); extern char* strcpy(char*, const char*); extern int strlen(const char*);

const TBLSZ = 23; name* table[TBLSZ];

name* look(char* p; int ins) (* /* ... */ *)

Π—Π°ΠΌΠ΅Ρ‚ΡŒΡ‚Π΅, Ρ‡Ρ‚ΠΎ table.c сам описываСт стандартныС Ρ„ΡƒΠ½ΠΊΡ†ΠΈΠΈ для Ρ€Π°Π±ΠΎΡ‚Ρ‹ со строками, поэтому Π½ΠΈΠΊΠ°ΠΊΠΎΠΉ ΠΏΡ€ΠΎΠ²Π΅Ρ€ΠΊΠΈ согласованости этих описаний Π½Π΅Ρ‚. ΠŸΠΎΡ‡Ρ‚ΠΈ всСгда Π»ΡƒΡ‡ΡˆΠ΅ Π²ΠΊΠ»ΡŽΡ‡Π°Ρ‚ΡŒ Π·Π°Π³ΠΎΠ»Π²ΠΎΡ‡Π½Ρ‹ΠΉ Ρ„Π°ΠΉΠ», Ρ‡Π΅ΠΌ ΠΎΠΏΠΈΡΡ‹Π²Π°Ρ‚ΡŒ имя Π² .c Ρ„Π°ΠΉΠ»Π΅ ΠΊΠ°ΠΊ extern. ΠŸΡ€ΠΈ этом ΠΌΠΎΠΆΠ΅Ρ‚ Π²ΠΊΠ»ΡŽΡ‡Π°Ρ‚ΡŒΡΡ «слишком ΠΌΠ½ΠΎΠ³ΠΎΒ», Π½ΠΎ это ΠΎΠ±Ρ‹Ρ‡Π½ΠΎ Π½Π΅ ΠΎΠΊΠ·Ρ‹Π²Π°Π΅Ρ‚ ΡΠ΅Ρ€ΡŒΠ΅Π·Π½ΠΎΠ³ΠΎ влияния Π½Π° врСмя, Π½Π΅ΠΎΠ±Ρ…ΠΎΠ΄ΠΈΠΌΠΎΠ΅ для ΠΊΠΎΠΌΠΏΠΈΠ»Ρ†ΠΈΠΈ, ΠΈ ΠΊΠ°ΠΊ ΠΏΡ€Π°Π²ΠΈΠ»ΠΎ экономит врСмя программиста. Π’ качСствС ΠΏΡ€ΠΈΠΌΠ΅Ρ€Π° этого, ΠΎΠ±Ρ€Π°Ρ‚ΠΈΡ‚Π΅ Π²Π½ΠΈΠΌΠ°Π½ΠΈΠ΅ Π½Π° Ρ‚ΠΎ, ΠΊΠ°ΠΊ strlen() Π·Π°Π½ΠΎΠ²ΠΎ описываСтся Π² main() (Π½ΠΈΠΆΠ΅). Π­Ρ‚ΠΎ лишниС наТатия клавиш ΠΈ Π²ΠΎΠΌΠΎΠΆΠ½Ρ‹ΠΉ источник нСприятностСй, ΠΏΠΎΡΠΊΠΎΠ»ΡŒΠΊΡƒ компилятор Π½Π΅ ΠΌΠΎΠΆΠ΅Ρ‚ ΠΏΡ€ΠΎΠ²Π΅Ρ€ΠΈΡ‚ΡŒ ΡΠΎΠ³Π»Π°ΡΠΎΠ²Π°Π½Π½ΠΎΡΡ‚ΡŒ этих Π΄Π²ΡƒΡ… ΠΎΠΏΡ€Π΅Π΄Π΅Π»Π΅Π½ΠΈΠΉ. На самом Π΄Π»Π΅, этой слоТности ΠΌΠΎΠΆΠ½ΠΎ Π±Ρ‹Π»ΠΎ Π±Ρ‹ ΠΈΠ·Π±Π΅ΠΆΠ°Ρ‚ΡŒ, Π±ΡƒΠ΄ΡŒ всС описания extern ΠΏΠΎΠΌΠ΅Ρ‰Π΅Π½Ρ‹ Π² dc.h, ΠΊΠ°ΠΊ ΠΈ ΠΏΡ€Π΅Π΄Π»Π°Π³Π°Π»ΠΎΡΡŒ ΡΠ΄Π΅Π»Π°Ρ‚ΡŒ. Π­Ρ‚Π° Β«Π½Π΅Ρ€Π΅ΠΆΠ½ΠΎΡΡ‚ΡŒΒ» сохранСна Π² ΠΏΡ€ΠΎΠ³Ρ€Π°ΠΌΠΌΠ΅, ΠΏΠΎΡΠΊΠΎΠ»ΡŒΠΊΡƒ это ΠΎΡ‡Π΅Π½ΡŒ Ρ‚ΠΈΠΏΠΈΡ‡Π½ΠΎ для C ΠΏΡ€ΠΎΠ³Ρ€Π°ΠΌΠΌ, ΠΎΡ‡Π΅Π½ΡŒ ΡΠΎΠ±Π»Π°Π·Π½ΠΈΡ‚Π΅Π»ΡŒΠ½ΠΎ для программиста, ΠΈ Ρ‡Π°Ρ‰Π΅ ΠΏΡ€ΠΈΠ²ΠΎΠ΄ΠΈΡ‚, Ρ‡Π΅ΠΌ Π½Π΅ ΠΏΡ€ΠΈΠ²ΠΎΠ΄ΠΈΡ‚, ΠΊ ошибкам, ΠΊΠΎΡ‚ΠΎΡ€Ρ‹Π΅ Ρ‚Ρ€ΡƒΠ΄Π½ΠΎ ΠΎΠ±Π½Π°Ρ€ΠΆΠΈΡ‚ΡŒ, ΠΈ ΠΊ ΠΏΡ€ΠΎΠ³Ρ€Π°ΠΌΠΌΠ°ΠΌ, с ΠΊΠΎΡ‚ΠΎΡ€Ρ‹ΠΌΠΈ тяТСло Ρ€Π°Π±ΠΎΡ‚Π°Ρ‚ΡŒ. Вас ΠΏΡ€Π΅Π΄ΡƒΡ€Π΅Π΄ΠΈΠ»ΠΈ!

И main.c, Π½Π°ΠΊΠΎΠ½Π΅Ρ†, выглядит Ρ‚Π°ΠΊ:

// main.c: инициализация, Π³Π»Π°Π²Π½Ρ‹ΠΉ Ρ†ΠΈΠΊΠ» ΠΈ ΠΎΠ±Ρ€Π°Π±ΠΎΡ‚ΠΊΠ° ошибок

#include Β«dc.hΒ»

int no_of_errors;

double error(char* s) (* /* ... */ *)

extern int strlen(const char*);

main(int argc, char* argv[]) (* /* ... */ *)

Π’Π°ΠΆΠ½Ρ‹ΠΉ случай, ΠΊΠΎΠ³Π΄Π° Ρ€Π°Π·ΠΌΠ΅Ρ€ Π·Π°Π³ΠΎΠ»ΠΎΠ²ΠΎΡ‡Π½Ρ‹Ρ… Ρ„Π°ΠΉΠ»ΠΎΠ² станвится ΡΠ΅Ρ€ΡŒΠ΅Π·Π½ΠΎΠΉ ΠΏΠΎΠΌΠ΅Ρ…ΠΎΠΉ. Набор Π·Π°Π³ΠΎΠ»ΠΎΠ²ΠΎΡ‡Π½Ρ‹Ρ… Ρ„Π°ΠΉΠ»ΠΎΠ² ΠΈ Π±ΠΈΠ±Π»ΠΈΠΎΡ‚Π΅ΠΊΡƒ ΠΌΠΎΠΆΠ½ΠΎ ΠΈΡΠΏΠΎΠ»ΡŒΠ·ΠΎΠ²Π°Ρ‚ΡŒ для Ρ€Π°ΡΡˆΠΈΡ€Π΅Π½ΠΈΡ языка мноТСством ΠΎΠ±Ρ‰ΠΈ ΡΠΏΠ΅Ρ†ΠΈΠ°Π»ΡŒΠ½ΠΎΠΏΡ€ΠΈΠΊΠ»Π°Π΄Π½Ρ‹Ρ… Ρ‚ΠΈΠΏΠΎΠ² (см. Π“Π»Π°Π²Ρ‹ 5-8). Π’ Ρ‚Π°ΠΊΠΈΡ… случаях Π½Π΅ принято ΠΎΡΡƒΡ‰Π΅ΡΡ‚Π²Π»ΡΡ‚ΡŒ Ρ‡Ρ‚Π΅Π½ΠΈΠ΅ тысяч строк Π·Π°Π³ΠΎΠ»ΠΎΠ²ΠΎΠ½Ρ‹Ρ… Ρ„Π°ΠΉΠ»ΠΎΠ² Π² Π½Π°Ρ‡Π°Π»Π΅ ΠΊΠ°ΠΆΠ΄ΠΎΠΉ компиляции. Π‘ΠΎΠ΄Π΅Ρ€ΠΆΠ°Π½ΠΈΠ΅ этих Ρ„Π°ΠΉΠ»ΠΎΠ² ΠΎΠ±Ρ‹Ρ‡Π½ΠΎ Β«Π·Π°ΠΌΠΎΡ€ΠΎΠΆΠ΅Π½ΠΎΒ» ΠΈ измСняСтся ΠΎΡ‡Π΅Π½ΡŒ нСчасто. НаиболСС ΠΏΠ»Π΅Π·Π½Ρ‹ΠΌ ΠΌΠΎΠΆΠ΅Ρ‚ ΠΎΠΊΠ°Π·Π°Ρ‚ΡŒΡΡ ΠΌΠ΅Ρ‚ΠΎΠ΄ Π·Π°Ρ‚Ρ€Π°Π²ΠΊΠΈ компилятора содСрТаниСм этих Π·Π°Π³ΠΎΠ»ΠΎΠ²ΠΎΡ‡Π½Ρ‹Ρ… Ρ„Π°Π»ΠΎΠ². По сути, создаСтся язык ΡΠΏΠ΅Ρ†ΠΈΠ°Π»ΡŒΠ½ΠΎΠ³ΠΎ назначСния со своим собствСнным компилятором. Никакого стадартного ΠΌΠ΅Ρ‚ΠΎΠ΄Π° создания Ρ‚Π°ΠΊΠΎΠ³ΠΎ компилятора с Π·Π°Ρ‚Ρ€Π°Π²ΠΊΠΎΠΉ Π½Π΅ принято.

4.3.2 ΠœΠ½ΠΎΠΆΠ΅ΡΡ‚Π²Π΅Π½Π½Ρ‹Π΅ Π·Π°Π³ΠΎΠ»ΠΎΠ²ΠΎΡ‡Π½Ρ‹Π΅ Ρ„Π°ΠΉΠ»Ρ‹

Π‘Ρ‚ΠΈΠ»ΡŒ разбиСния ΠΏΡ€ΠΎΠ³Ρ€Π°ΠΌΠΌΡ‹ с ΠΎΠ΄Π½ΠΈΠΌ Π·Π°Π³ΠΎΠ»ΠΎΠ²ΠΎΡ‡Π½Ρ‹ΠΌ Ρ„Π°ΠΉΠ»ΠΎΠΌ Π½Π°ΠΈΠ±ΠΎΠ»Π΅Π΅ ΠΏΡ€ΠΈΠ³ΠΎΠ΄Π΅Π½ Π² Ρ‚Π΅Ρ… случаях, ΠΊΠΎΠ³Π΄Π° ΠΏΡ€ΠΎΠ³Ρ€Π°ΠΌΠΌΠ° Π½Π΅Π²Π΅Π»ΠΈΠΊΠ° ΠΈ Π΅Π΅ части Π½Π΅ прСдполагаСтся ΠΈΡΠΏΠΎΠ»ΡŒΠ·ΠΎΠ²Π°Ρ‚ΡŒ ΠΎΡ‚Π΄Π΅Π»ΡŒΠ½ΠΎ. ΠŸΠΎΡΡ‚ΠΎΠΌΡƒ Ρ‚ΠΎ, Ρ‡Ρ‚ΠΎ Π½Π΅Π²ΠΎΠ·ΠΌΠΎΠΆΠ½ΠΎ ΡƒΡΡ‚Π°Π½ΠΎΠ²ΠΈΡ‚ΡŒ, ΠΊΠ°ΠΊΠΈΠ΅ описания Π·Π°Ρ‡Π΅ΠΌ ΠΏΠΎΠΌΠ΅Ρ‰Π΅Π½Ρ‹ Π² Π·Π°Π³ΠΎΠ»ΠΎΠ²ΠΎΡ‡Π½Ρ‹ΠΉ Ρ„Π°ΠΉΠ», нСсущСствСнно. ΠŸΠΎΠΌΠΎΡ‡ΡŒ ΠΌΠΎΠ³ΡƒΡ‚ ΠΊΠΎΠΌΠΌΠ΅Π½Ρ‚Π°Ρ€ΠΈΠΈ. Π”Ρ€ΡƒΠ³ΠΎΠΉ способ – ΡΠ΄Π΅Π»Π°Ρ‚ΡŒ Ρ‚Π°ΠΊ, Ρ‡Ρ‚ΠΎΠ±Ρ‹ каТдая Ρ‡Π°ΡΡ‚ΡŒ ΠΏΡ€ΠΎΠ³Ρ€Π°ΠΌΠΌΡ‹ ΠΈΠΌΠ΅Π»Π° свой Π·Π°Π³ΠΎΠ»ΠΎΠ²ΠΎΡ‡Π½Ρ‹ΠΉ Ρ„Π°ΠΉΠ», Π² ΠΊΠΎΡ‚ΠΎΡ€ΠΎΠΌ ΠΎΠΏΡ€Π΅Π΄Π΅Π»ΡΡŽΡ‚ΡΡ прСдотавляСмыС этой Ρ‡Π°ΡΡ‚ΡŒΡŽ срСдства. Π’ΠΎΠ³Π΄Π° ΠΊΠ°ΠΆΠ΄Ρ‹ΠΉ .c Ρ„Π°ΠΉΠ» ΠΈΠΌΠ΅Π΅Ρ‚ ΡΠΎΠΎΡ‚Π²Π΅Ρ‚ΡΡ‚Π²ΡƒΡŽΡ‰ΠΈΠΉ .h Ρ„Π°ΠΉΠ», ΠΈ ΠΊΠ°ΠΆΠ΄Ρ‹ΠΉ .c Ρ„Π°ΠΉΠ» Π²ΠΊΠ»ΡŽΡ‡Π°Π΅Ρ‚ свой собтвСнный (ΡΠΏΠ΅Ρ†ΠΈΡ„ΠΈΡ†ΠΈΡ€ΡƒΡŽΡ‰ΠΈΠΉ Ρ‚ΠΎ, Ρ‡Ρ‚ΠΎ Π² Π½Π΅ΠΌ задаСтся) .h Ρ„Π°ΠΉΠ» ΠΈ, Π²ΠΎΠ·ΠΌΠΎΠΆΠ½ΠΎ, Π½Π΅ΠΊΠΎΡ‚ΠΎΡ€Ρ‹Π΅ Π΄Ρ€ΡƒΠ³ΠΈΠ΅ .h Ρ„Π°ΠΉΠ»Ρ‹ (ΡΠΏΠ΅Ρ†ΠΈΡ„ΠΈΡ†ΠΈΡ€ΡƒΡŽΡ‰ΠΈΠ΅ Ρ‚ΠΎ, Ρ‡Ρ‚ΠΎ Π΅ΠΌΡƒ Π½ΡƒΠΆΠ½ΠΎ).

Рассматривая ΠΎΡ€Π³Π°Π½ΠΈΠ·Π°Ρ†ΠΈΡŽ ΠΊΠ°Π»ΡŒΠΊΡƒΠ»ΡΡ‚ΠΎΡ€Π°, ΠΌΡ‹ Π·Π°ΠΌΠ΅Ρ‡Π°Π΅ΠΌ, Ρ‡Ρ‚ΠΎ error() ΠΈΡΠΏΠΎΠ»ΡŒΠ·ΡƒΠ΅Ρ‚ΡΡ ΠΏΠΎΡ‡Ρ‚ΠΈ ΠΊΠ°ΠΆΠ΄ΠΎΠΉ Ρ„ΡƒΠ½ΠΊΡ†ΠΈΠ΅ΠΉ ΠΏΡ€ΠΎΠ³Ρ€Π°ΠΌΠΌΡ‹, Π° сама ΠΈΡΠΏΠΎΠ»ΡŒΠ·ΡƒΠ΅Ρ‚ Ρ‚ΠΎΠ»ΡŒΠΊΠΎ Β«stream.hΒ». Π­Ρ‚ΠΎ обычная для Ρ„ΡƒΠ½ΠΊΡ†ΠΈΠΈ ошибок ситуация, поэтому error() слСдуСт ΠΎΡ‚Π΄Π΅Π»ΠΈΡ‚ΡŒ ΠΎΡ‚ main():

// error.h: ΠΎΠ±Ρ€Π°Π±ΠΎΡ‚ΠΊΠ° ошибок

extern int no_errors;

extern double error(char* s);

// error.c

#include Β«stream.hΒ» #include Β«error.hΒ»

int no_of_errors;

double error(char* s) (* /* ... */ *)

ΠŸΡ€ΠΈ Ρ‚Π°ΠΊΠΎΠΌ стилС использования Π·Π°Π³ΠΎΠ»ΠΎΠ²ΠΎΡ‡Π½Ρ‹Ρ… Ρ„Π°ΠΉΠ»ΠΎΠ² .h Ρ„Π°ΠΉΠ» ΠΈ связанный с Π½ΠΈΠΌ .c Ρ„Π°ΠΉΠ» ΠΌΠΎΠΆΠ½ΠΎ Ρ€Π°ΡΡΠΌΠ°Ρ‚Ρ€ΠΈΠ²Π°Ρ‚ΡŒ ΠΊΠ°ΠΊ ΠΌΠ΄ΡƒΠ»ΡŒ, Π² ΠΊΠΎΡ‚ΠΎΡ€ΠΎΠΌ .h Ρ„Π°ΠΉΠ» Π·Π°Π΄Π°Π΅Ρ‚ интСрфСйс, Π° .c Ρ„Π°ΠΉΠ» Π·Π°Π΄Π°Π΅Ρ‚ Ρ€Π΅Π°Π»ΠΈΠ·Π°Ρ†ΠΈΡŽ. Π’Π°Π±Π»ΠΈΡ†Π° символов Π½Π΅ зависит ΠΎΡ‚ ΠΎΡΡ‚Π°Π»ΡŒΠ½ΠΎΠΉ части ΠΊΠ°Π»ΡŒΠΊΡƒΠ»ΡΡ‚ΠΎΡ€Π° Π·Π° ΠΈΡΠΊΠ»ΡŽΡ‡Π΅Π½ΠΈΠ΅ΠΌ использования Ρ„ΡƒΠ½ΠΊΡ†ΠΈΠΈ ошибок. Π­Ρ‚ΠΎ ΠΌΠΎΠΆΠ½ΠΎ ΡΠ΄Π΅Π»Π°Ρ‚ΡŒ явным:

// table.h: описания Ρ‚Π°Π±Π»ΠΈΡ†Ρ‹ ΠΈΠΌΠ΅Π½

struct name (* char* string; name* next; double value; *);

extern name* look(char* p, int ins = 0); inline name* insert(char* s) (* return look(s,1); *)

// table.c: опрСдСлСния Ρ‚Π°Π±Π»ΠΈΡ†Ρ‹ ΠΈΠΌΠ΅Π½

#include Β«error.hΒ» #include Β«string.hΒ» #include Β«table.hΒ»

const TBLSZ = 23; name* table[TBLSZ];

name* look(char* p; int ins) (* /* ... */ *)

Π—Π°ΠΌΠ΅Ρ‚ΡŒΡ‚Π΅, Ρ‡Ρ‚ΠΎ описания Ρ„ΡƒΠ½ΠΊΡ†ΠΈΠΉ Ρ€Π°Π±ΠΎΡ‚Ρ‹ со строками Ρ‚Π΅ΠΏΠ΅Ρ€ΡŒ Π²ΠΊΠ»ΡŽΡ‡Π°ΡŽΡ‚ΡΡ ΠΈΠ· Β«string.hΒ». Π­Ρ‚ΠΎ ΠΈΡΠΊΠ»ΡŽΡ‡Π°Π΅Ρ‚ Π΅Ρ‰Π΅ ΠΎΠ΄ΠΈΠ½ Π²ΠΎΠ·ΠΌΠΎΠΆΠ½Ρ‹ΠΉ источник ошибок.

// lex.h: описания для Π²Π²ΠΎΠ΄Π° ΠΈ лСксичСского Π°Π½Π°Π»ΠΈΠ·Π°

enum token_value (* NAME, NUMBER, END, PLUS='+', MINUS='-', MUL='*', DIV='/', PRINT=';', ASSIGN='=', LP='(', RP=')' *);

extern token_value curr_tok; extern double number_value; extern char name_string[256];

extern token_value get_token();

Π­Ρ‚ΠΎΡ‚ интСрфСйс лСксичСского Π°Π½Π°Π»ΠΈΠ·Π°Ρ‚ΠΎΡ€Π° достаточно бСпорядочСн. НСдостаток Π² Π½Π°Π΄Π»Π΅ΠΆΠ°Ρ‰Π΅ΠΌ Ρ‚ΠΈΠΏΠ΅ лСксСмы ΠΎΠ±Π½Π°Ρ€ΡƒΠΆΠΈΠ²Π°Π΅Ρ‚ сСбя Π² нСобходимости Π΄Π°Π²Π°Ρ‚ΡŒ ΠΏΠΎΠ»ΡŒΠ·ΠΎΠ²Π°Ρ‚Π΅Π»ΡŽ get_token() фактчСскиС лСксичСскиС Π±ΡƒΡ„Π΅Ρ€Ρ‹ number_value ΠΈ name_string.

// lex.c: опрСдСлСния для Π²Π²ΠΎΠ΄Π° ΠΈ лСксичСского Π°Π½Π°Π»ΠΈΠ·Π°

#include Β«stream.hΒ» #include Β«ctype.hΒ» #include Β«error.hΒ» #include Β«lex.hΒ»

token_value curr_tok; double number_value; char name_string[256];

token_value get_token() (* /* ... */ *)

Π˜Π½Ρ‚Π΅Ρ€Ρ„Π΅ΠΉΡ синтаксичСского Π°Π½Π°Π»ΠΈΠ·Π°Ρ‚ΠΎΡ€Π° ΡΠΎΠ²Π΅Ρ€ΡˆΠ΅Π½Π½ΠΎ ΠΏΡ€ΠΎΠ·Ρ€Ρ‡Π΅Π½: // syn.c: описания для синтаксичСского Π°Π½Π°Π»ΠΈΠ·Π° ΠΈ вычислСния

extern double expr(); extern double term();

extern double prim();

// syn.c: опрСдСлСния для синтаксичСского Π°Π½Π°Π»ΠΈΠ·Π° ΠΈ // вычислСния

#include Β«error.hΒ» #include Β«lex.hΒ» #include Β«syn.hΒ»

double prim() (* /* ... */ *) double term() (* /* ... */ *) double expr() (* /* ... */ *)

Главная ΠΏΡ€ΠΎΠ³Ρ€Π°ΠΌΠΌΠ°, ΠΊΠ°ΠΊ всСгда, Ρ‚Ρ€ΠΈΠ²ΠΈΠ°Π»ΡŒΠ½Π°:

// main.c: главная ΠΏΡ€ΠΎΠ³Ρ€Π°ΠΌΠΌΠ°

#include Β«stream.hΒ» #include Β«error.hΒ» #include Β«lex.hΒ» #include Β«syn.hΒ» #include Β«table.hΒ» #include Β«string.hΒ»

main(int argc, char* argv[]) (* /* ... */ *)

Бколько Π·Π°Π³ΠΎΠ»ΠΎΠ²ΠΎΡ‡Π½Ρ‹Ρ… Ρ„Π°ΠΉΠ»ΠΎΠ² ΠΈΡΠΏΠΎΠ»ΡŒΠ·ΠΎΠ²Π°Ρ‚ΡŒ Π² ΠΏΡ€ΠΎΠ³Ρ€Π°ΠΌΠΌΠ΅, зависит ΠΎΡ‚ ΠΌΠ½ΠΎΠ³ΠΈΡ… Ρ„Π°ΠΊΡ‚ΠΎΡ€ΠΎΠ². МногиС ΠΈΠ· этих Ρ„Π°ΠΊΡ‚ΠΎΡ€ΠΎΠ² сильнСС связаны с Ρ‚Π΅ΠΌ, ΠΊΠ°ΠΊ ваша систСма Ρ€Π°Π±ΠΎΡ‚Π°Π΅Ρ‚ с Π·Π°Π³ΠΎΠ»ΠΎΠ²ΠΎΡ‡Π½Ρ‹ΠΌΠΈ Ρ„Π°Π»Π°ΠΌΠΈ, Π½Π΅ΠΆΠ΅Π»ΠΈ с Π‘++. НапримСр, Ссли Π² вашСм Ρ€Π΅Π΄Π°ΠΊΡ‚ΠΎΡ€Π΅ Π½Π΅Ρ‚ срСдств, ΠΏΠΎΠ·Π²ΠΎΠ»ΡΡŽΡ‰ΠΈΡ… ΠΎΠ΄Π½ΠΎΠ²Ρ€Π΅ΠΌΠ΅Π½Π½ΠΎ Π²ΠΈΠ΄Π΅Ρ‚ΡŒ нСсколько Ρ„Π°ΠΉΠ»ΠΎΠ², использованиС большого числа Ρ„Π°ΠΉΠ»ΠΎΠ² становится ΠΌΠ΅Π½Π΅Π΅ ΠΏΡ€ΠΈΠ²Π»ΠΊΠ°Ρ‚Π΅Π»ΡŒΠ½Ρ‹ΠΌ. Аналогично, Ссли ΠΎΡ‚ΠΊΡ€Ρ‹Π²Π°Π½ΠΈΠ΅ ΠΈ Ρ‡Ρ‚Π΅Π½ΠΈΠ΅ 10 Ρ„Π°ΠΉΠ»ΠΎΠ² ΠΏΠΎ 50 строк Π² ΠΊΠ°ΠΆΠ΄ΠΎΠΌ Ρ‚Ρ€Π΅Π±ΡƒΠ΅Ρ‚ Π·Π°ΠΌΠ΅Ρ‚Π½ΠΎ большС Π²Ρ€Π΅ΠΌΠ΅Π½ΠΈ, Ρ‡Π΅ΠΌ Ρ‡Ρ‚Π΅Π½ΠΈΠ΅ ΠΎΠ΄Π½ΠΎΠ³ΠΎ Ρ„Π°ΠΉΠ»Π° Π² 500 строк, Π²Ρ‹ ΠΌΠΎΠΆΠ΅Ρ‚Π΅ Π΄Π²Π°ΠΆΠ΄Ρ‹ ΠΏΠΎΠ΄ΡƒΠΌΠ°Ρ‚ΡŒ, ΠΏΡ€Π΅ΠΆΠ΄Π΅ Ρ‡Π΅ΠΌ ΠΈΡΠΏΠΎΠ»ΡŒΠ·ΠΎΠ²Π°Ρ‚ΡŒ Π² нСбольшом ΠΏΡ€ΠΎΠ΅ΠΊΡ‚Π΅ ΡΡ‚ΠΈΠ»ΡŒ мноТСствСнных Π·Π³ΠΎΠ»ΠΎΠ²ΠΎΡ‡Π½Ρ‹Ρ… Ρ„Π°ΠΉΠ»ΠΎΠ². Π‘Π»ΠΎΠ²ΠΎ прСдостСрСТСния: Π½Π°Π±ΠΎΡ€ ΠΈΠ· дСсяти Π·Π³ΠΎΠ»ΠΎΠ²ΠΎΡ‡Π½Ρ‹Ρ… Ρ„Π°ΠΉΠ»ΠΎΠ² плюс стандартныС Π·Π°Π³ΠΎΠ»ΠΎΠ²ΠΎΡ‡Π½Ρ‹Π΅ Ρ„Π°ΠΉΠ»Ρ‹ ΠΎΠ±Ρ‹Ρ‡Π½ΠΎ Π»Π΅Π³Ρ‡Π΅ ΠΏΠΎΠ΄Π΄Π°ΡŽΡ‚ΡΡ ΡƒΠΏΡ€Π°Π²Π»Π΅Π½ΠΈΡŽ. Π‘ Π΄Ρ€ΡƒΠ³ΠΎΠΉ стороны, Ссли Π²Ρ‹ Ρ€Π°Π·Π±ΠΈΠ»ΠΈ описания Π² большой ΠΏΡ€ΠΎΠ³Ρ€Π°ΠΌΠΌΠ΅ Π½Π° логичСски ΠΌΠΈΠ½ΠΈΠΌΠ°Π»ΡŒΠ½Ρ‹Π΅ ΠΏΠΎ Ρ€Π°ΠΌΠ΅Ρ€Ρƒ Π·Π°Π³ΠΎΠ»ΠΎΠ²ΠΎΡ‡Π½Ρ‹Π΅ Ρ„Π°ΠΉΠ»Ρ‹ (помСщая ΠΊΠ°ΠΆΠ΄ΠΎΠ΅ описаниС структуры Π² свой ΠΎΡ‚Π΄Π΅Π»ΡŒΠ½Ρ‹ΠΉ Ρ„Π°ΠΉΠ» ΠΈ Ρ‚.Π΄.), Ρƒ вас Π»Π΅Π³ΠΊΠΎ ΠΌΠΎΠΆΠ΅Ρ‚ ΠΏΠΎΠ»ΡƒΡ‡ΠΈΡ‚ΡŒΡΡ Π½Ρ€Π°Π·Π±Π΅Ρ€ΠΈΡ…Π° ΠΈΠ· сотСн Ρ„Π°ΠΉΠ»ΠΎΠ².