1.57k likes | 1.69k Views
Перемноження матриць. #include "stdafx.h" using namespace System; using namespace System::IO; int main(array<System::String ^> ^args) { String^s; int n,m; Console::WriteLine("Enter n="); s=Console::ReadLine(); n=Convert::ToInt32(s); Console::WriteLine("Enter m=");
E N D
Перемноження матриць #include "stdafx.h" using namespace System; using namespace System::IO; int main(array<System::String ^> ^args) { String^s; int n,m; Console::WriteLine("Enter n="); s=Console::ReadLine(); n=Convert::ToInt32(s); Console::WriteLine("Enter m="); s=Console::ReadLine(); m=Convert::ToInt32(s);
array<double,2>^x=gcnew array<double,2>(n,m); array<double,2>^y=gcnew array<double,2>(m,n); array<double,2>^c=gcnew array<double,2>(n,n); StreamReader^sr=gcnew StreamReader("D:\\AVRPROG\\VISUAL\\TestFile20"); for(int i=0;i<n;i++) for(int j=0;j<m;j++) { s=sr->ReadLine(); x[i,j]=Convert::ToDouble(s); Console::WriteLine("x={0}",x[i,j]); } for(int i=0;i<m;i++) for(int j=0;j<n;j++) { s=sr->ReadLine(); y[i,j]=Convert::ToDouble(s); Console::WriteLine("y={0}",y[i,j]); }
//sr->Close(); StreamWriter^sw=gcnew StreamWriter("D:\\AVRPROG\\VISUAL\\TestFile21.txt"); sw->AutoFlush::set(true); for(int i=0;i<n;i++) for(int j=0;j<n;j++) { c[i,j]=0; for(int k=0;k<m;k++) c[i,j]+=x[i,k]*y[k,j]; Console::WriteLine("c={0}",c[i,j]); if(j%n==0) sw->Write("\n"); sw->Write(" c[{0},{1}]={2} ",i,j,c[i,j]); } Console::WriteLine(L"Finish"); return 0; }
TestFile20 • 1 • 2,5 • 3 • 4 • 5 • 6,7 • 8 • 10 • 20 • 30 • 40 • 50 • 60 • 70 • 80
Елементи компіляції Аналіз формальних мов
Відомості про регулярні вирази та граматики • Алфавіт – конечна множина I елементів, які наз. СИМВОЛАМИ. • Ланцюжок (слово)- конечна послідовність символів із алфавіту I. • Мова в алфавіті I – довільна множина ланцюжків (слів).
Дії над ланцюжками xn- ланцюжокxповторюється n раз. xR - ланцюжок xпишеться в зворотномунапрямку. XY – за ланцюжком X розміщується Y. X* - ланцюжок xповторюється в циклі НУЛЬ і більше раз. X+- ланцюжок xповторюється в циклі ОДИН і більше раз.
| X | - довжина ланцюжка. { } або έабоe– пустий ланцюжок. [X] необов’язковий ланцюжок.
Регулярні вирази і граматика • Нехай три символи { , * | }не входять до заданого алфавіту символів I. Ланцюжок із об’єднанняI U { , * | } наз. регулярним виразом. Граматика G=( T, N, P, S) T, N - алфавіти термінальних і нетермінальних символів.
P - множина правил для отримання нетермінальних символів через термінальні та інші нетермінальні символи. S - стартовий або головний нетермінальний символ. intx, y, z; DVARB - >intl iden ( ‘ , ’ iden) * ’;’ PROG->(DVARB | DCONST| DFUNC) *eof
G=(T, N, P, S) T={x, y, w, z} N={ S, A, B } P={A->AB, A ->x, A ->y, B->w, B->z} L(G)={xw, yw, xz, yz}
Розширені граматики A i - > r i, де A iналежать до N r i – регулярні вирази із T U N. A1 – головний. S - >AB A - >x|y B - > w|z
T = { вино, пиво, каша, борщ, м’ясо, чай, кофе} N = {ОБІД, АЛКОГОЛЬ, ЇЖА, ПИТНЕ} ОБІД - > АЛКОГОЛЬ* ЇЖА ПИТНЕ АЛКОГОЛЬ - >вино| пиво ЇЖА- >борщ м’ясо| каша ПИТНЕ - >чай |кофе
Задачі аналізу Дано слово і граматика. Перевірити, що слово належить до мови, яка описана цією граматикою. Приклад: Дано слово [ [ x ] ] G=(T,N,P,S T={ [ , ], x, +} N={A,B} P={A->x, A->[B], B->A, B->B+A} LA(1) – аналіз. Стратегії зверху – вниз і знизу – вверх. A ═> [B] ═> [A] ═> [[B]] ═> [[A]] ═> [[x]]
Синтаксичні діаграми Орієнтований граф з двома вершинами: вхідною і вихідною.
1) Не повинно бути непомічених дуг. • 2) При розгалуженні дуги повинні починатися не з однакових термінальних символів. • Проходженню дуги, поміченої термінальним символом, відповідає розпізнавання цього символу у вхідному ланцюжку і зсув на наступний символ, якщо розпізнавання відбулося. Інакше – повідомлення про помилку.
Проходженню дуги, поміченої нетермінальним символом, наприклад А, відповідає виклик відповідної функції розпізнавання ланцюжків, які виводяться з нього. Перед викликом цієї функції потрібно, щоб був прочитаний ПЕРШИЙ ТЕРМІНАЛЬНИЙ символ X, який виводять із А. • Функція успішно аналізує ланцюжок W, якщо у відповідності до синтаксичної діаграми відбувається попадання із вхідної вершини у вихідну при прочитанні символу за символом усього ланцюжка.
Введення в компіляцію • Транслятор – програма, яка перекладаєпрограму із вхідної мови (алгоритмічної) на еквівалентну їй об’єктну програму. • Якщо вхідна мова високого рівня, а вихідною є машинна мова або асемблер, то такий транслятор наз. компілятором. • Інтерпретатор– різновидність транслятора, який перекладає на мову простих проміжних команд і виконує її. • Препроцесор перекладає із однієї мови високого рівня на іншу. Застосовується як частина компілятора.
ЛА – лексичний аналізатор. Об’єднує символи в лексеми: • Ключові і службові слова; • Ідентифікатори; • Знаки операцій; • Знаки пунктуації; • Числа; • Признак кінця файлу.
СА – синтаксичний аналізатор. Будує із лексем синтаксичні структури, які можуть бути складовими інших структур (константи, змінні, вирази, функції і т. п.). • ГПК – генерація проміжного коду. • ОК – оптимізація коду. • ГК – генерація коду.
Мова SPL Символи: 1) Букви: A ÷ Z, a ÷ z 2) 0 ÷ 9 3) + - * / % ( ) , ; = \n \t Ідентифікатор – букви або букви і цифри, але першою повинна бути буква. До 40 символів. \n , \t та пропуски не можна вживати в ідентифікаторах. Константи – тільки цілічисла.
Змінні тільки цілого типу: глобальні і локальні. Службові слова:begin, end, read, print, return, if, then,do, while, int, const – 11 слів. Функції: Ім’я (формальні параметри) begin локальні змінні і константи Оператори end
Описання констант: • const a=12, b=4, d=- 5, s=0; • Описання змінних: • int x, y, z, teta ; • Оператори закінчуються крапкою з комою. Перед end крапку з комою не ставити. • Одна із функцій повинна бути main() • Дані в функцію передаються лише по значенню. • Результат повертається або через return або через глобальні змінні. • Допускаються рекурсії.
Конструкцияif ifвиразthenпослідовністьоператорів end; оператор_1; Якщо результат обчислення виразу більше нуля, то виконується послідовність операторів за ключовим словомthen, якщо менше або дорівнює нулю ( ≤ ), то ця послідовність пропускається, і відбувається перехід до наступного за if оператора...
Конструкцияwhile whileвиразdoпослідовність_операторів end; опер1; ... Якщо результат обчислення виразу більше нуля, то виконується послідовність операторів за ключовим словом do,після чого знову обчислюється вираз. Якщо результат менше або дорівнює нулю ( ≤ ), то ця послідовність пропускається, і відбувається вихід із циклу.
Програма лексичного аналізу Прочитати текст програми на SPL, розпізнати лексеми і занести ідентифікатори в таблицю ідентифікаторівchar TNM[400]; Ідентифікатори та їхні адреси занести в файл.
В програмі кожній лексемі відповідає ціле число. Для символів це код із таблиці ASCII. Для ключових слів цілі числа задаються за допомогою перераховуваних констант( enum). • enum {BEGINL=257, ENDL, READL, PRITL, RETRL, IFL, THENL, WHILEL, DOL, CONSTL, INTL, IDEN, NUMB}; • Признак кінця файлу в stdio.h • #define EOF -1
Програма лексичного аналізу #include<stdio.h> #include<stdlib.h> #include<ctype.h> #include<conio.h> #include<alloc.h> #include<string.h> /*Кодилексем ключових слів мови SPL*/ enum { BEGINL=257, ENDL, IFL, THENL, WHILEL, DOL, RETRL, READL, PRITL, INTL, CONSTL, IDEN, NUMB };
int nst=0; //номер рядка в тексті на SPL int lex;// лексема (ціле число) int lval; //значення лексеми (для констант це число, а для ідентифікаторів – їхніадреси в таблиціchar TNM[400]) char nch='\n'; // символ, який читається із тексту програми на SPL FILE*PF,*padres;//файл із текстом програми на SPL і файл для результатів void get(void); void number(void); void word(void); char*add(char*nm);
void main( int ac,char*av[ ] ) { clrscr( ); if(!ac) { puts(“Немає файлу із програмою"); exit(1); } PF=fopen(av[1],"r"); padres=fopen("getrez.dan","w"); if(!PF) puts("Файл не відкривається"); else get( );// Виклик функції для отримання лексеми }
void get() { while(nch!=EOF) { while(isspace(nch)) { if( nch= = '\n‘ ) nst++; nch = getc(PF); }
If ( isdigit ( nch ) ) number( ); else if( isalpha ( nch ) ) word(); else if(nch= ='(‘ || nch= =')‘ || nch= =',‘ || nch= = ';‘ ||nch== ‘=' ||nch= ='+‘ ||nch= ='-‘ ||nch= ='*‘ || nch=='/‘ || nch= =‘%‘) { lex=nch; nch=getc(PF); } } if(nch= =EOF) lex=EOF; else puts("Hедопустимийсимвол"); return; }
void number() { for( lval=0; isdigit( nch ); nch= getc(PF)) lval=lval*10+nch - '0'; lex= NUMB; return; }
void word( ) { int cdl [ ]={BEGINL,ENDL,IFL,THENL,WHILEL,DOL, RETRL,READL,PRITL,INTL,CONSTL,IDEN,NUMB}; char*serv [ ]={"begin", "end", "if", "then“, "while", “do", "return", “read", "print", "int", "const“ }; int i; char tx[40]; char*p; for(p=tx; isdigit(nch) || isalpha(nch); nch=getc(PF)) *( p++ ) = nch; *p='\0';
for( i=0; i<11; i++) if( strcmp ( tx, serv [ i ] ) == 0) { lex=cdl [ i ]; return; } lex=IDEN; lval= (int) add ( tx ); printf("Адреса для %s =%p\n",tx,lval); fprintf(padres,"Адресадля %s =%p\n",tx,lval); return; }
char TNM[400];//таблиця ідентифікаторів char*ptn=TNM; //покажчик на перший вільний елемент в таблиці TNM[400 ] //******************************************* char*add(char*nm) { char*p; for(p=TNM;p<ptn;p+=strlen(p)+1) if(strcmp(p,nm)==0) return p; if((ptn+=strlen(nm)+1)>TNM+400) { puts("Переповнення таблиці ідентифікаторів"); exit( 1 ); } return ( strcpy ( p, nm ) ); }
Повний синтаксис мови SPL • Алфавіт термінальних символів – лексеми. • Нетермінальні символи: • PROG, DFUNC, DCONST, DVARB, CONS, PARAM, BODY, STML, STAT, EXPR, TERM, FACT, FCTL.
Регулярні вирази PROG - >(DCONST |DVARB| DFUNC )* eof DCONST -> constl CONS (‘,’ CONS) * ‘;’ CONS - >iden ‘=’ [‘+’ | ’-’] numb DVARB -> intl iden (‘,’ iden)* ’;’ DFUNC -> iden PARAM BODY PARAM -> ’(‘ [ iden (‘,’ iden)* ] ‘)’ BODY->beginl (DVARB| DCONST)* STML endl STML - > STAT (‘;’ STAT)*
STAT- >iden ‘=’ EXPR | readl iden | pritl EXPR | retrl EXPR | ifl EXPR thenl STML endl |whilel EXPR dol STML endl //************************************************* EXPR- >[‘+’ | ‘-’] TERM ((‘+’ | ‘-’) TERM)*
TERM - > FACT((‘*’|’/’|’%’) FACT)* FACT- > ’(’ EXPR ‘)’ | numb | iden [‘(’ [FCTL] ’)’] FCTL - > EXPR (‘,’EXPR)*
Синтаксичні діаграми і функції розпізнавання ланцюжків для нетермінальнихсимволів