Преобразование строчных букв в заглавные

Это тоже полезное действие, которое часто применяется в системах хране­ния и поиска данных. Дело в том, что при сравнении строк обязательно учитывается регистр, поэтому такие способы записи одного слова, как ком­пьютер, компьютер и компьютер будут восприняты как три разных слова, а в отсортированном списке они будут располагаться даже не рядом друг с другом. Учитывая данное обстоятельство, обычно при вводе информации выполняют преобразование слова к буквам какого-то одного регистра, чаще к заглавным буквам.

Начнем с простого примера. Преобразуем все строчные английские буквы введенной строки в заглавные. Для этого достаточно знания одной функ­ции upcase, которая преобразует к верхнему регистру один символ (лис­тинг 9.7).


I Листинг9.7. Преобразование строчных латинских букв в заглавные

var s : string/­procedure upstring(var s:string); ) процедура преобразования строки } var i: integer; begin

for i:=l to length(s) do

s[i]:=upcase(s[i]); { преобразование одного символа } end; begin { начало основной программы }

write('Введите исходную строку:');readln{з);

upstring(s); writeln(s); readln; end.

Усложним задачу. Пусть требуется преобразовать в строке строчные буквы русского алфавита в заглавные. Функция upcase с символами русского алфа­вита не работает. Придется писать свою функцию, работающую с русскими буквами.

Будем использовать две вспомогательные строки: строку из всех заглавных букв русского алфавита и строку всех строчных букв. Заметим, что здесь обязательным является применение типизированных констант (или пере­менных), т. к. обычная строковая константа не может интерпретироваться как массив символов (листинг 9.8).

Г Листинг 9.8. Преобразование русских букв в заглавные

var s:string;

function upstringrus(s:string):string; const small :з^1пд='абвгдежзиклмнопрстуфхцчишгьыьэюя' ; big:s tring='АБВГДЕЖЗИКЛ1даОПРСТУФХЦЧШЩЬЫЬЭЮЯ'; var i,n:integer; begin

for i:=l to lengthfs) do begin

n:=pos{s[i],small);{ находим номер символа в строке строчных букв ) if n>0 then s[i]:=big[n];{ заглавная буква с таким же номером }

end;

upstringrus:=s; end; begin

write('Введите строку');readln(s);

writeln(upstringrus(s)); readln; end.


Чтобы окончательно закрыть эту тему, приведем заключительный пример. Процедура getupstr преобразует русские и английские буквы в заглавные непосредственно при вводе. Буква вводится в любом регистре, а на экра­не — всегда заглавная. Такой способ ввода используется в различных про­граммах, теперь есть возможность узнать, как это делается (листинг 9.9).

^Листинг 9.9. Ввод строки с приведением всех букв к верхнему регистру

uses crt;

var s:string;

procedure getupstr(var st: string);

var с:char;

begin

st:='';{ сформировали пустую строй^ — это действие нельзя забывать } repeat

c:=readkey;{ слепой ввод без отображения на экране — модуль crt } case с of

{коды заглавных и прописных русских букв от А до П различаются на 32, } 'а1 .. 'п1: c:=chr(ord(c)-32);

т .. 'я1: c:=chr(ord(c)-80); { а коды от Р до Я - на 80 } 'а1 .. -z': c:=upcase(c);


end;

 

if c<>#13 then { не клавиша <Enter> } begin

st:=st+c; write(с);{ добавляем символ к строке и выводим } end;

until c=#13;{ ввод завершен нажатием клавиши <Enter> } writeln; end; "begin

writeln('Введите строку текста и нажмите <Enter>'); getupstr(s); writeln('Значение s:1); writeln(s); readln


Множества

Множества имеют большое значение в математике, поэтому не удивитель­но, что в языке Turbo Pascal имеется такой тип данных.

Понятие множества

Множество — это набор элементов одинакового типа, которые рассматри­ваются как единое целое. Элементы множества не пронумерованы, следова­тельно, нельзя обратиться к отдельному элементу множества по его индексу. Поэтому множества используются в тех задачах, где порядок следования элементов данных не имеет значения (например, множество гласных или согласных букв, множество ходов шахматной фигуры из определенного по­ложения и т. д.).

Тип элементов множества называется базовым типом множества. Область значений типа множества — набор всевозможных подмножеств, составлен­ных из элементов базового типа.

В языке Turbo Pascal имеются ограничения на базовый тип. Это может быть только порядковый тип, количество значений которого не превышает 256. Из простых типов к таким относятся char, byte, boolean. Разрешается ис­пользовать перечисляемый тип и диапазон (если он включает не больше 256 элементов).

Это существенные ограничения, которые не позволяют использовать мно­жества в серьезных задачах обработки данных. Все же для ряда задач при­менение множеств может обеспечить серьезные преимущества по сравне­нию с использованием других структур данных — массивов или строк.

При задании значений элементов множества применяются квадратные скобки.

Например: [1,2,3,4], ['а','Ь','с1Ь ['а' .. 'г'}


Если множество не имеет элементов, оно называется пустым и обознача­ется []. Пустое множество включено в любое другое.

Для объявления множественного типа используется словосочетание set of (множество из ...). Формат объявления множественных типов следующий:

Type

ИмяТипа = set of ТипЭлементовМножества; var

ИмяПеременной, ... : ИмяТипа;

Можно описать переменные множественного типа и без предварительного объявления типа:

var ИмяПеременной, ... : set ofТип;

Можно объявить константы множественного типа:

const ИмяКонстанты=[ЗначениеМножества];

а также типизированные константы:

constИмяКонстанты:ТипМножест'ва= [ЗначениеМножества] ;

Например:

const number - [1,4,7,9]; type simply = set of 'a'.-'h1;

var pr : simply;

letter : set of char; {без предварительного описания в разделе типов}

В данном примере в множество рг могут входить значения символов латин­ского алфавита от 'а' до 'h1; в множество letter — значения любых сим­волов. Попытка присвоить другие значения вызовет ошибку выполнения.

Замечание

В памяти множества представлены особым образом. Каждому значению базо­вого типа множества в памяти отводится 1 бит (не байт!). Следовательно, мак­симальный размер ячейки памяти, отводимой под множество, составляет 32 байта. Поскольку все значения порядкового типа расположены строго по по­рядку, 1 в соответствующем бите означает наличие данного значения в множественной переменной, а 0 — отсутствие.

Исходя из особенностей внутреннего представления множеств, можно сде­лать два основных вывода:

П в множестве не может быть одинаковых элементов, что согласуется и с нашими математическими знаниями;

П все операции над множествами выполняются значительно эффективней, чем над другими структурами данных.


Операции над множествами

При работе с множествами допускается использование следующих операций:

П отношения (=, <>, >=, <=);

О объединения множеств (+);

О пересечения множеств (*);

П разности множеств (—);

G проверка принадлежности элемента множеству (in).

Рассмотрим каждую из операций в отдельности.

П Операция "равно" (=). Два множества А л Л считаются равными, если они состоят из одних и тех же элементов. Порядок следования элементов в сравниваемых множествах значения не имеет (табл. 10.1).

Таблица 10.1. Примеры операции "равно"

"\ Операция "не равно" (<>). Два множества А и В считаются не равными, если они отличаются по количеству элементов или по значению хотя бы одного элемента (табл. 10.2).

Таблица 10.2. Примеры операции "не равно"

П Операция "больше или равно" (>=). Эта операция используется для опреде­ления принадлежности одного множества другому. Результат операции А>~В равен true, если все элементы множества В содержатся в множест­ве А. В противном случае результат равен false (табл. 10.3).


3 Операция "меньше или равно" (<=). Операция используется аналогично предыдущей операции, но результат выражения А<=В равен true, если все элементы множества А содержатся в множестве В. В противном слу­чае результат равен false (табл. 10.4).

" V

Таблица 10.4. Примеры операции "меньше или равно"

О Операция in. Эта операция используется для проверки принадлежности какого-либо значения указанному множеству. Она обычно применяется в условных операторах (табл. 10.5).

Таблица 10.5. Примеры операции in

Операция in позволяет эффективно и наглядно производить сложные проверки условий, заменяя иногда десятки других операций. Например,

СЛОЖНОе условиеif (a=l) or (а=2) or (a=3) or (a=4) or (a=5) then ...

можно заменить более коротким выражением if a in [1 .. 5] then ...

Часто операцию in пытаются записать с отрицанием: х not in m. Такая запись является ошибочной, правильная инструкция имеет вид: not(x in m)


П Объединение множеств (+). Объединением двух множеств является третье множество, содержащее элементы обоих множеств (табл. 10.6).

Таблица 10.6. Примеры операции объединения множеств

П Пересечение множеств (*). Пересечением двух множеств является третье множество, которое содержит элементы,* входящие одновременно в оба множества (табл. 10.7).

Таблица 10.7. Примеры операции пересечения множеств

П Разность множеств (—). Разностью двух множеств является третье мно­жество, которое содержит элементы первого множества, не входящие во второе множество (табл. Ю.8).

Таблица 10.8. Примеры операции разности множеств

Листинг 10.1 содержит небольшую программу, демонстрирующую операции над множествами. Множества чисел заполнены следующим образом: D1 -четными числами 2, 4, 6, 8; множество D2 — числами О, 1, 2, 3, 5; множест­во D3 — нечетными числами 1, 3, 5, 7, 9. После этого над множествами вы­полнены операции объединения, разности, пересечения.


; Листинг 10.1, Операции над множествами

type digits=set of 0 .. 9;

var dl,d2,d3,d : digits;

begin

dl:=[2,4,6,8]; ( заполнение множеств }

d2:=[0 .. 3,5];

d3:-[l,3,5,7,9J;

d:=dl+d2; { объединение множеств dl и d2 )

d:=d+d3; { объединение множеств d и d3 }

d:=d~d2; { разность множеств d и d2 )

d:=d*dl; { пересечение множеств d и dl }

end.

!

Так как в Turbo Pascal отсутствуют средства ввода/вывода элементов множе­ства, то действие программы можно проверить, исполняя ее по шагам и на­блюдая текущие значения переменных dl, 62, d3, d в окне просмотра (см. приложение 1).

Тем не менее, нетрудно написать процедуру для вывода элементов множе­ства. Например, процедура для вывода множества символов может иметь следующий вид:

type charset=set of char; procedure writeset(a:charset); var с:char; begin

for c:=chr(0) to chr(255) do

if с in a then write(c,' '); writeln; end;

Обратите внимание — значения элементов множества с помощью этой про­цедуры всегда будут выводиться в упорядоченном виде. Это не удивительно, т. к. в памяти они находятся в упорядоченном виде.

Рассмотрим следующий пример, демонстрирующий проверку принадлежно­сти элемента множеству. Пусть требуется в предложении, введенном с кла­виатуры, определить количество гласных букв. Программа для решения этой задачи приводится в листинге 10.2.

\ Л истин); 10.2. Подсчет количества гласных букв в предложении

const

glasn=[ 'а', 'е', 'и', 'о1, 'у'/ 'ьг', тэ', 'ю1, 'я',

•и' ' F ' ' И ' ' Г)' ' V ' ' W' ' Ч ' ' HV ' Я' 1 •

г\ , И, г VI f w, J I Е* t -Э г № r /1J/


var s:string; p,i:integer; begin

write('Введите строку текста: '); readln(s);

p:=0;

for i:=l to length(s) do

if s[i] in glasn then p:=p+l;

writelnf'B строке ',р, ' гласных букв'); readln; end.

Комментарии j

В программе используется константа glasn, представляющая множество глас­ных букв. Проверка принадлежности символов предложения множеству глас­ных букв записывается операцией in. Разумеется, для решения этой задачи можно было бы записать вспомогательную строку из гласных букв и использо­вать функцию роз для поиска буквы в этой строке. Однако вариант с множест­вом предпочтительней, т. к. текст получился нагляднее, кроме того, проверка на принадлежность множеству выполняется намного быстрей, чем поиск символа в строке.

Формирование