Манипулирование символами
Символ записывается в текущий выходной поток с помощью следующей цели: putt CJ
где С — код ASCII (число от С до 127) выводимого символа. Например, вопрос ?- put( 65}, put( 66;, put( 67) вызывает вывод следующих данных: ABC
где 65 — код ASCII символа "А",66 — символа "В" и 67 — символа "С".
Отдельный символ может быть считан из текущего входного потока с помощью цели getO( С]
Эта цель вызывает чтение текущего символа из входного потока и конкретизацию
переменной с значением кода ASCII этого символа. Вариантом предиката явля-
ется get, который используется для чтения непробельных символов (символов, отличных от пробела, знака табуляции и т.п.). Поэтому цель get{ С)
вызывает пропуск всех непечатаемых символов (в частности, пробелов) от текущей позиции ввода во входном потоке вплоть до первого печатаемого символа. После этого, как обычно, считывается данный символ и переменная С конкретизируется значением его кода ASCII.
В качестве примера использования предикатов, передающих отдельные символы,
определим процедуру squeeze, предназначенную для выполнения следующей зада
чи: вводить текст из текущего входного потока и выводить тот же текст, переформа
тированный таким образом, что несколько пробелов между словами заменяются оди
нарными пробелами. Для простоты предположим, что любой текст, обрабатываемый
процедурой squeeze, оканчивается точкой и что слова разделены одним или не
сколькими пробелами, а не другими символами. В таком случае допустимые входные
данные имеют вид
The robot tried to pour wine out of the bottle.
Цель squeeze выведет этот текст в следующей форме: The robot tried to pour wine out of the bottle.
Процедура squeeze имеет такую же структуру, как и процедуры обработки файлов, приведенные в предыдущем разделе. Вначале ока считывает первый символ и выводит его, после чего выполняет остальную часть алгоритма обработки, в зависимости от этого символа. При этом могут рассматриваться три варианта, которые соответствуют следующим случаям: символ представляет собой точку, пробел или букву. Взаимное исключение этих трех вариантов достигается в программе с помощью операторов отсечения, как показано ниже.
saueeze :-getOt С), putt О, dorest ( С) .
dorest t 46) :- !. f «G - это код точки в кодировке ASCII; вся работа выполнена dorest. ( 32) :-\, % 32 - это код пробела в кодировке ASCII
get( С) , * Пропустить остальные пробелы
put( С) ,
dorest С с) . dorest( Letter):-
squeeze.
Глава 6. Ввод и вывод 143
Упражнение
6.3. Обобщите процедуру squeeze, чтобы она позволяла также обрабатывать запятые. Необходимо удалять все пробелы, которые непосредственно предшествуют занятым, а после каждой запятой должен находиться один пробел.