Добавил:
Upload Опубликованный материал нарушает ваши авторские права? Сообщите нам.
Вуз: Предмет: Файл:

bobalo(1)

.pdf
Скачиваний:
588
Добавлен:
12.02.2016
Размер:
1.24 Mб
Скачать

Лабораторна робота № 6

СИМВОЛЬНІ МАСИВИ. РЯДКОВИЙ ТИП

У МОВІ TURBO PASCAL

111

1. МЕТА РОБОТИ

Мета роботи – ознайомитись з окремим видом масивів – строками, або рядками символів.

2. ТЕОРЕТИЧНІ ВІДОМОСТІ

Під час розв’язування різних задач на ЕОМ виникає необхідність використання рядків, або рядків символів. У задачах лексичного і синтаксичного аналізу, а також при обробці текстової інформації, основним об’єктом обробки є рядки. Для позначення у програмі наперед визначеної послідовності символів слугує рядок-константа. Рядок-константа – це послідовність символів між двома одинарними апострофами, наприклад:

’Львівська політехніка’

’Введи X,Y’

Якщо в середині рядка-константи є апостроф, то він подвоюється:

’Вимкни комп’’ютер’ ’Опиши об’’єкт’

Символ ’ (апостроф) у мові Паскаль використовується як обмежувач ряд- ків-констант. Тому транслятор не переплутає тип константи, якщо вона стоїть між апострофами.

Наприклад:

25 – ціла константа, ’25’ – рядок-константа.

Кожна з цих констант міститься у пам’яті машини по-різному: 25 –0000000000011001 – у двійковій системі ’25’ – 0011001000110101,

де 00110010 – код цифри 2 та 00110101 – код цифри 5 в системі ASCII. Відповідно і операції над цими двома константами можуть виконуватись різні: число 25 може брати участь в арифметичних операціях, а рядкова

константа ’25’ у таких операціях використовуватись не може.

2.1. СИМВОЛЬНІ МАСИВИ

Переважно конкретна послідовність символів не є наперед відомою, а формується у процесі виконання програми. Тому в мові Паскаль використовуються, крім рядкових констант, і рядкові змінні – одновимірні масиви, елементами яких є символи:

VAR ST:ARRAY [1..50] OF CHAR;

112

Ми описали рядкову змінну ST, яка є рядком з п’ятдесяти символів. Типом індексу такого масиву повинен бути інтервальний цілий тип.

Мова Паскаль має додаткові засоби для роботи з такими масивами. Оскільки на етапі розроблення мови Паскаль оперативна пам'ять машини

була дуже обмежена, то для більшої економії пам’яті Вірт розробив алгоритм зменшення обсягу пам’яті за рахунок упакування символьних змінних.

В авторській версії мови Паскаль рядкові змінні подано у вигляді упакованого масиву, елементи якого максимально ефективно займають пам’ять машини за рахунок упакування декількох компонентів в одне поле пам’яті.

Опис упакованого масиву:

VAR TS: PACKED ARRAY[1..50] OF CHAR;

Упакований масив використовується у програмі так само, як і не упакований, але програми з такими масивами виконуються дещо повільніше, оскільки необхідний додатковий час на вибір компонентів з масиву.

Для зменшення часу можна використати процедури PACK та UNPACK для упакування та розпакування масивів. Упаковані масиви (строки) мають ті самі властивості, що і звичайні масиви, але є і деякі відмінності:

1. Рядковій змінній можна присвоїти значення рядкової константи. При цьому треба пам’ятати, що довжини рядкової константи і змінної повинні бути однакові:

VAR ST1:PACKED ARRAY[1..22]OF CHAR;

BEGIN

ST1: = ’ЛьвівськаПолітехніка’;

де – символ пропуску (пробілу).

Пропуск є значущим символом, і тому рядки можна доповнювати відповідною кількістю пропусків.

2. Над рядковими змінними і рядковими константами можуть викону-

ватись операції порівняння: >, >=, <, <=, =, < >.

Порівняння проводиться посимвольно, тому довжина рядків символів, що порівнюються, повинна бути однаковою.

Наприклад, порівняти: ’АВС’ > ’ABL’

Така операція дасть результат FALSE, оскільки буква С стоїть раніше ніж

буква L, тобто C<L.

3. Над рядковими масивами може виконуватись операція конкатенації + (приєднання) при виведенні:

S1 = ’Львівська’;

S2 = ’Політехніка’; WRITELN(S1 + ’’ + S2);

У результаті виконання оператора WRITELN на екрані висвітиться:

Львівська Політехніка

113

4. До рядків символів може застосуватись стандартна функція EOLN, яка

дає значення TRUE, якщо зчитано останній символ вхідного рядка, і значення

FALSE, якщо кінця рядка не досягнуто.

 

 

 

 

Приклад 1: У реченні завдовжки не більше 80 символів обчислити

кількість входжень буквосполучень FOR.

 

 

 

 

Блок-схему алгоритму наведено на рис. 1.

 

 

 

 

1

 

 

 

Блок 3 – введення першої і другої букви

 

Початок

 

символьного рядка.

 

 

 

2

 

 

 

Блок 4 – початок циклу. Введення третьої

k =0

 

букви.

 

 

 

 

 

 

 

 

 

 

 

 

 

Блок 5 –

перевірка,

чи знайдено

сло-

 

 

 

 

3

Ввід

 

во FOR.

 

 

 

 

 

 

Блок 8 – перевірка, чи досягнуто кінця

ST[1], ST[2]

 

 

 

S[1], S[2]

 

рядка.

 

 

 

 

4

 

 

 

Програма має такий вигляд:

 

Ввід

 

PROGRAM KFOR (INPUT, OUTPUT);

 

 

ST[3]

 

VAR ST:PACKAD ARRAY[1..3] OF CHAR;

 

S[3]

 

 

 

 

K: INTEGER;

 

 

 

 

5

ні

BEGIN

 

 

 

 

 

ST='FOR'

 

K:= 0;

 

 

 

 

 

так

 

WRITELN (’Введи речення’);

 

 

 

READ(ST[1], ST[2]);

 

 

6

 

 

REPEAT

 

 

 

 

 

 

 

READ(ST[3]);

 

 

 

k = k+1

 

 

 

 

 

 

 

 

IF ST = ’FOR’ THEN K:= K+1;

7

 

 

 

ST[1]: = ST[2];

 

 

 

 

 

ST[2]: = ST[3]

 

 

ST[1] = ST[2]

 

 

 

 

 

UNTIL EOLN;

 

 

 

ST[2] = ST[3]

 

WRITELN(’Кількість

буквосполучень

 

 

 

ні

8

 

FOR=’, K)

 

 

 

 

 

END.

 

 

 

 

 

 

EOLN

 

 

Приклад 2:

у реченні завдовжки до 80-ти

 

 

 

 

9 так

 

символів обчислити кількість входжень слів

 

“FOR”.

 

 

 

 

 

Вивід

 

 

Якщо в тексті шукаємо слова, а не букво-

 

k

 

 

 

 

сполучення, то треба пам’ятати, що слово від

10

 

 

слова

відділяється

пропуском

(пробілом ’_’ ). І

 

Кінець

 

тому не достатньо перевірити тільки три символи,

 

 

 

Рис. 1. Блок-схема

щоб

вони збігалися

із словами FOR;

треба

перевірити і пропуски, які мають стояти біля

 

алгоритму

 

 

 

відповідного слова.

 

 

 

114

1

 

 

 

 

 

ПОЧАТОК

 

 

2

 

 

 

 

 

3

 

 

 

 

Ввід рядка

 

 

4

К=0

 

 

 

 

 

5

 

 

 

НІ

 

 

 

 

 

Str[1]=’F’

Str[2]=’O’

 

 

Str[3]=’R’

Str[4]=‘ ‘

 

6

 

 

ТАК

 

K=K+1

ТАК

 

 

 

 

7

 

 

 

 

І=1,76

 

 

8

Str[I]=’ ’ Str[I+1]=’F’

НІ

 

 

 

Str[I+2]=’O’

 

 

Str[I+3]=‘R‘

Str[I+4]=’ ‘

 

9

 

 

ТАК

 

К=K+1

 

 

 

 

 

 

10

 

 

НІ

 

 

 

 

 

Str[77]=’ ’

Str[78]=’F’

 

 

Str[79]=’O’

Str[80]=‘R‘

 

11

 

 

ТАК

 

K=K+1

 

 

 

 

 

12

Вивід результату

 

 

 

13

КІНЕЦЬ

Рис. 3.Блок-схема алгоритму

115

Для прикладу маємо рядок:

FOR ABSFOR FOR FOREWER FOR

Тут слово FOR зустрічається тричі:

1)на початку рядка у вигляді ”FOR ” – чотири символи;

2)всередині рядка у вигляді ” FOR ” – п’ять позицій;

3)укінці рядка у вигляді ” FOR” – чотири позиції.

Крім того, в рядку є ще два словосполучення FOR, але в цьому завданні вони нас не цікавлять. Тобто ми повинні передбачити в програмі всі три варіанти, в яких може бути слово FOR. Блок-схему алгоритму наведено на рис. 2.

Програма:

PROGRAM SLFOR(INPUT, OUTPUT); VAR STR:ARRAY[1..80] OF CHAR; K,I:INTEGER;

BEGIN

WRITELN(’ВВЕДИ РЕЧЕННЯ’); FOR I:=1 TO 80 DO

READ(STR[I]);

K:=0;

{’FOR’ НА ПОЧАТКУ РЯДКА}

IF(STR[1]=’F’)AND(STR[2]=’O’)AND(STR[3]=’R’) AND(STR[4]=’ ’)THEN K:=K+1;

{СЛОВО FOR ВСЕРЕДИНІ РЯДКА}

FOR I:=1 TO 76 DO

IF(STR[I]=’ ’)AND(STR[I+1]=’F’)AND(STR[I+2]=’O’) AND(STR[I+3]=’R’)AND (STR[I+4]=’ ’ THEN K:=K+1;

{СЛОВО FOR В КІНЦІ РЯДКА}

IF(STR[77]=’ ’)AND(STR[78]=’F’)AND(STR[79]=’O’) AND(STR[80]=’R’)THEN K:=K+1; WRITELN(’КІЛЬКІСТЬ СЛІВ FOR=’,K);

END.

2.2. РЯДКОВИЙ ТИП У МОВІ TURBO PASCAL

Рядковий тип є одним із розширень мови Паскаль, реалізованих у середовищі Turbo Pascal. Рядковий тип випливає з поняття символьних масивів, але в рядковому типі може змінюватись довжина рядка.

Рядковий тип визначає множину символьних ланцюжків довільної довжини (від нуля до заданого числа). Для опису рядкового типу використовується службове слово STRING, за яким вказується максимальна довжина рядка.

Структура опису типу:

TYPE <ім’я типу>=STRING[<довжина рядка>];

116

Синтаксична діаграма:

STRING

[

константний

]

вираз

 

 

 

Рис. 3. Синтаксиксична діаграма рядкового типу

Приклад:

TYPE ST = STRING[80]; VAR TX : ST;

Зміна ТХ є рядком символів завдовжки від нуля до 80 символів. Описати зміну рядкового типу можна і в розділі опису змінних:

VAR TX : STRING[80]; S : STRING;

Максимальна довжина рядка може бути задана цілим числом або іменованою константою цілого типу, а може і не вказуватись. Якщо довжина не вказана, то максимальною довжиною є число 255.

Отже, найважливішою відмінністю рядка від символьного маcиву є те, що рядки можуть змінювати свою довжину.

Наприклад:

S: = ’ЛьвівськаПолітехніка’;

S:= ’Національнийуніверситет’ + S;

Урезультаті виконання цих двох операторів присвоєння змінна S матиме значення:

’НаціональнийуніверситетЛьвівськаПолітехніка’

де – символ пропуску (пробілу).

Хоча, на перший погляд, пам’ять під змінну рядкового типу виділяється динамічно, проте це не так. Точніше, пам’ять виділяється так, як і для масивів на етапі трансляції програми за максимальною довжиною. Якщо максимальна довжина рядка 80 символів, то виділяється 81 байт. При цьому в 80-ти байтах записується рядок символів, а в нульовому байті – довжина цього рядка:

0

1

2

3

4

 

N-1 N

4

A

B

C

D

 

Зайнята частина рядка

 

Вільна частина рядка

Нехай описана зміна:

VAR ST : STRING[80]; BEGIN

SТ: = ’ABCD’,

117

Унульовий байт запишеться довжина рядка ST – 4, а у перший, другий, третій і четвертий байти символи A,B,C,D. Решта 76 байтів будуть вільними.

Над змінними рядкового типу можуть виконуватися операції.

1)конкатенації ( + ). Наприклад: ST:= ST + ’LM’

Урезультаті виконання цієї операції рядок ST вже міститиме 6 символів: ‘ABCDLM’.

2)порівняння: >, > =, <, < =, =, < >.

Під час виконання операцій порівняння діють такі правила:

1.Коротший рядок завжди менший від довшого;

2.Якщо довжина рядків однакова, то відбувається поелементне порівняння цих рядкiв з урахуванням лексикографічної впорядкованості значень стандартного символьного типу CHAR.

Значення рядкової змінної може бути присвоєно оператором присвоєння або прочитано з файла чи з клавіатури. При цьому треба пам’ятати, що якщо рядковій змінній присвоюється значення довше, ніж максимальна довжина, рядок “обрубується” до максимальної довжини:

VAR ST : STRING[15];

BEGIN

ST: = ’Державнийуніверситет’

WRITELN(ST);

У результаті виконання такого фрагмента програми виведеться:

Державний уніве

Є два способи роботи із рядками символів:

1.Представити рядок у вигляді символьного масиву.

2.Працювати з рядком як з єдиним цілим за допомогою функцій і процедур.

2.2.1. Робота з символьним рядком, представленим масивом символів

(стандарт мови Паскаль)

На змінну рядкового типу переносяться всі властивості та правила роботи

зсимвольними масивами.

1.Введення і виведення рядка здійснюється поелементно в циклі за допомогою процедур READ та WRITE.

2.Доступ до окремого елемента рядка здійснюється з використанням індекса, тобто ST[1], ST[I].

Приклад: у символьному рядку завдовжки 80 символів визначити кількість входжень слів IN, вважаючи, що всі слова розділені пропусками. При вирішенні цього завдання доцільно передбачити три ситуації:

118

1

Початок

2 i = 1, 80

3 Ввід

ST[i]

4

k =0

5 ST[1]='I'

так

6

ST[2]='N'

 

k =k+1

ST[3]=' '

 

 

ні

 

 

7

 

так

8

 

ST[78]='

'

 

ST[79]='I'

 

k =k+1

 

ST[80]='N'

 

 

 

ні

 

 

 

9

iI=1,7776

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

10

 

 

 

 

 

 

 

 

 

 

 

ST[i]='

 

 

'

 

так

 

 

 

 

 

 

 

11

 

 

 

 

 

 

ST[i+1]='I'

 

 

 

 

k =k+1

 

ST[i+2]='N'

 

 

 

 

 

 

 

 

 

 

 

ST[i+3]='

 

'

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

ні

12

Вивід k

13

Кінець

Рис.3 Блок-схема алгоритму

Блок-схему алгоритму представлено на рис. 3.

Блоки 2, 3 – введення рядка символів завдовжки 80.

Блок 4 – обнулення лічильника К. Блоки 5, 6 – перевірка, чи слово IN стоїть на початку рядка.

Блоки 7, 8 – перевірка, чи слово IN стоїть в кінці рядка.

Блок 9 – відкриття циклу.

Блок 10 – перевірка, чи слово IN стоїть всередині рядка.

Блок 11 – збільшення лічильника на

1.

Блок 12 – виведення результату К.

Рис. 4. Блок-схема алгоритму

119

1.Слово IN стоїть на початку рядка, тобто ’IN ’;

2.Cлово IN стоїть всередині рядка, тобто ’ IN ’;

3.Cлово IN в кінці рядка, тобто ’ IN’.

Текст програми:

PROGRAM SIMMAS(INPUT,OUTPUT); VAR ST : ARRAY[1..80] OF CHAR;

I,K : INTEGER; BEGIN

FOR I: = 1 TO 80 DO

READ(ST[I]); K: =0;

IF (ST[1]=’I’) AND (ST[2]=’N’) AND (ST[3]=’ ’)THEN K:=K+1;

IF (ST[78]=’ ’) AND (ST[79]=’I’) AND (ST[80]=’N’)THEN K:=K+1;

FOR I:=1 TO 76 DO

IF(ST[I]=’ ’)AND(ST[I+1]=’I’)AND(ST[I+2]=’N’) AND(ST[I+3]=’ ’)

THEN K:=K+1; WRITELN(’Кількість слів IN=’, K)

END.

2.2.2. Робота з символьними рядками як з єдиним цілим

(середовище Turbo Pascal)

Введення і виведення змінної рядкового типу здійснюється за допомогою процедур READLN та WRITELN без зазаначення індексу елемента.

READLN(ST);

WRITELN(ST);

Над змінними рядкового типу визначені такі стандартні функції:

1.LENGTH(<рядок>) – визначає довжину рядка, тобто кількість символів у цьому рядку.

2.CONCAT(S1, S2,…,SN) – з’єднує рядки S1, S2, …SN в один рядок.

3.COPY(S, IND, K) – дає підрядок, виділений із рядка S, завдовжки К,

починаючи з індекса IND;

4. POS(SP, S) – дає номер позиції, з якої починається підрядок SP в рядку S.

Стандартні процедури:

5.DELETE(S, IND, K) – вилучає К символів із рядка S, починаючи з позиції IND.

6.INSERT(S1, S , IND) – вставляє S1 в рядок S, починаючи з позиції IND.

Звикористанням стандартних функцій та процедур до змінної рядкового

120

Соседние файлы в предмете [НЕСОРТИРОВАННОЕ]