- •Аннотация
- •Условия использования
- •Оглавление
- •Содержание
- •Только для взрослых
- •Десять лет спустя
- •Чему нас учат семья и школа?
- •Крошка сын к отцу пришел
- •Азбучные истины
- •Что я могу ещё сказать?
- •Благодарности
- •Детям до 16-ти
- •Глава 1 Путь далек у нас с тобою…
- •Компьютер
- •Компилятор
- •Личный багаж
- •Компьютерная литература
- •В здоровом теле – здоровый дух
- •Вместе весело шагать по просторам!
- •Повторение – мать учения
- •Соглашения
- •Итоги
- •Глава 2 Вместо теории
- •Миф о думающих машинах
- •Загадочные коды
- •Языки программирования и компиляторы
- •Следующий шаг –
- •Итоги
- •Глава 3 Консольный интерфейс
- •Что такое интерфейс?
- •Консольный интерфейс
- •Прикосновение к консольному интерфейсу
- •А почему не «окна»?
- •Итоги
- •Глава 4 Оружие – к бою!
- •Оружейный прилавок
- •Free Pascal
- •Настройка ярлыка
- •Free Pascal
- •Установка справочной системы
- •Обновление версий Free Pascal
- •Итоги
- •Глава 5 Программа номер один
- •Постановка задачи
- •Создание файла
- •Наполнение файла
- •Компиляция
- •Процедура вывода (печати)
- •Запуск программы
- •Итоги
- •Глава 6 Подготовка к следующему штурму
- •Ещё об исходных файлах
- •Управление окном редактора
- •Борьба с ошибками
- •Итоги
- •Глава 7 Развиваем успех
- •Операторы и разделители
- •Программа, стой!
- •Алгоритмы
- •Блок-схемы
- •Итоги
- •Глава 8 Постоянные и переменные
- •Константы
- •Идентификаторы
- •Переменные
- •Ввод и вывод данных
- •Итоги
- •А слабо?
- •Глава 9 Переменные: продолжение знакомства
- •Представьтесь, пожалуйста!
- •Из пустого в порожнее
- •Сцепление строк
- •Инициализация переменных
- •Типизированные константы
- •Итоги
- •А слабо?
- •Глава 10 Условный оператор
- •Стой! Кто идет?
- •Вопрос ребром
- •Пост номер один
- •Неполный условный оператор
- •Пост номер два
- •Итоги
- •А слабо?
- •Глава 11 Операторный блок
- •Операторные скобки
- •Красиво жить не запретишь
- •Комментарии
- •Итоги
- •Глава 12 Цикл с проверкой в конце
- •Подтянем дисциплину
- •Нанимаем репетитора
- •Вежливый часовой
- •Досрочный выход из цикла
- •Итоги
- •Глава 13 Правда и кривда
- •Есть ли жизнь на Марсе?
- •Информация и её мерило
- •Булевы переменные
- •Ввод и вывод булевых данных
- •Логические выражения
- •С высоты птичьего полета
- •Парад логических операций
- •Итоги
- •А слабо?
- •Глава 14 Дважды два – четыре
- •Поможем братьям нашим меньшим
- •Числа и действия с ними
- •Алгоритм экзаменатора
- •Экзаменатор, первый вариант
- •Итоги
- •А слабо?
- •Глава 15 Айда в Монте-Карло!
- •Куда ни глянь – то процедура, то функция!
- •Госпожа удача
- •Итоги
- •А слабо?
- •Глава 16 Делу время, а потехе час
- •Потемкинская лестница
- •Итоги
- •А слабо?
- •Глава 17 И вновь за парту
- •Цикл со счетчиком
- •Итоги
- •Глава 18 Аз, Буки
- •Символьный тип данных
- •Индексация
- •Длина строки
- •Распечатка строки
- •Итоги
- •Глава 19 Процедуры и функции: разделяй и властвуй
- •Снежный ком
- •Описание процедур
- •Процедуры с параметрами
- •Итоги
- •Глава 20 Процедуры: первый опыт
- •Мухи – налево, котлеты – направо!
- •Сверху вниз
- •Первые раны
- •Глобальные и локальные
- •Локально – это разумно!
- •Неподдающаяся строка
- •Итоги
- •Глава 21 Отладка
- •Отладчик
- •Жучки, вылезайте!
- •Ссылка на переменную
- •Итоги
- •Глава 22 О передаче параметров
- •Процедура обмена
- •Замена символов в строке
- •О передаче строк
- •Итоги
- •Глава 23 Функции
- •Объявление функции
- •Пример функции
- •Подсчет символов в строке
- •Возврат строк
- •Когда результат не важен
- •Неявная переменная Result
- •Итоги
- •Глава 24 Криптография
- •Секреты Юлия Цезаря
- •Суть проблемы
- •О кодировании символов
- •Чудесные превращения
- •Шифрование символа
- •Расшифровка символа
- •Итоги
- •А слабо?
- •Глава 25 Текстовые файлы
- •Файлы хорошие и разные
- •Формат текстовых файлов
- •Доступ к текстовым файлам
- •Чтение из файла
- •Последовательный доступ к файлу
- •Самореклама
- •Цикл с проверкой в начале
- •Итоги
- •Глава 26 Я не читатель, — я писатель!
- •Запись в текстовый файл
- •Пример записи в файл
- •Завершение шпионского проекта
- •Итоги
- •А слабо?
- •Глава 27 Дайте кораблю минутный отдых!
- •Ошибка ошибке рознь
- •Фатальные ошибки
- •«Простительные» ошибки
- •Опции компилятора
- •Обработка ошибок ввода-вывода
- •Директивы компилятора
- •Директиву – в студию!
- •Парад директив
- •Итоги
- •А слабо?
- •Глава 28 Редактор и справочная система
- •Небьющиеся окна
- •Буфер обмена
- •Справочная система
- •Итоги
- •Глава 29 Читайте по-новому
- •Полицейская база данных, версия 1
- •Полицейская база данных, версия 2
- •Итоги
- •Глава 30 Журнальная история
- •Статистика знает всё?
- •Строим планы
- •Барабаним по клавишам
- •Первый блин
- •Блин второй
- •Спецификатор ширины поля
- •«Развесные» числа
- •Итоги
- •Глава 31 Финал журнальной истории
- •Буква за буквой
- •Нелишняя предосторожность
- •Достройка программы
- •Испытание
- •Итоги
- •Глава 32 Порядковые типы данных
- •Типы данных: простые и сложные
- •Целое братство
- •Капля, переполняющая чашу
- •Инкремент и декремент
- •Диапазоны
- •Перечисления
- •Порядковые типы
- •Разумный контроль
- •Итоги
- •Глава 33 Вещественные числа
- •Изображение вещественных чисел
- •Вывод вещественных чисел
- •Типы вещественных чисел
- •Сравнение вещественных чисел
- •Типы данных пользователя
- •Совместимость и преобразование типов
- •Размеры переменных и типов данных
- •Итоги
- •Глава 34 Структура программы
- •Управляющие структуры
- •Структура программы
- •Структура процедур и функций
- •Обмен данными с подпрограммами
- •Встроенные процедуры и функции
- •Что дальше?
- •Итоги
- •А слабо?
- •Глава 35 Множества
- •В директорском кабинете
- •Первым делом, первым делом – оцифровка
- •Множества глазами математика
- •Числовые множества
- •Мощность множества, полные и неполные множества
- •Итоги
- •Глава 36 Множества в Паскале
- •Объявление множеств
- •Присвоение значений множествам
- •Операции с множествами
- •Сравнение множеств
- •Проверка на вхождение элемента в множество (операция IN)
- •Решение директорской задачи
- •Итоги
- •А слабо?
- •Глава 37 Ввод и вывод множеств
- •Вывод множества в текстовый файл
- •Ввод множества из текстового файла.
- •Директорская задача, первый вариант
- •Директорская задача, второй вариант
- •Итоги
- •Глава 38 Множества «в бою»
- •Активисты, шаг вперед!
- •Подвиг контрразведчика
- •В тридевятом царстве
- •Решето Эратосфена
- •Мелочь, а приятно
- •Итоги
- •А слабо?
- •Глава 39 Командная игра (массивы)
- •Снежная лавина
- •А где же волшебная палочка?
- •Массивы вокруг нас
- •Объявление массивов
- •Доступ к элементам (индексация)
- •Ввод и вывод массивов
- •Ошибки индексации
- •Итоги
- •Глава 40 Пристрелка на знакомых мишенях
- •Вопрос-ответ – добиваемся гибкости
- •Полицейская база данных – ускоряем поиск
- •Ещё раз о статистике
- •Итоги
- •Глава 41 По порядку, становись!
- •Пиратская справедливость
- •Пузырьковая сортировка
- •Электронная делёжка
- •Возвращение на футбольное поле
- •Итоги
- •Глава 42 Кто ищет, тот всегда найдет
- •Где эта улица, где этот дом?
- •Последовательный поиск
- •Двоичный поиск
- •Исследование двоичного поиска
- •Ах, время, время!
- •Логарифмы? Это просто!
- •Итоги
- •Глава 43 Сортировка по-взрослому
- •«Фермерская» сортировка
- •Быстрая сортировка
- •Процедура быстрой сортировки
- •О рекурсии и стеке
- •Алгоритмы, на старт!
- •Итоги
- •Глава 44 Строки
- •Строка – особый род массива
- •Укороченные строки
- •Операции со строками
- •Подсчет слов в строке
- •Контекстная замена
- •Итоги
- •Глава 45 Очереди и стеки
- •Вовочка в потоке событий
- •Танцевальный кружок
- •Скитания товарного вагона
- •Сортировочная горка
- •Итоги
- •Глава 46 Огромные числа
- •Сколько звезд на небе?
- •Сложение «в столбик» никто не отменял
- •Великая стройка
- •Длинная арифметика
- •Итоги
- •А слабо?
- •Глава 47 Системы счисления
- •Из тьмы веков
- •Число и его изображение
- •Десятичная система
- •Двоичная система
- •Шестнадцатеричная система
- •Другие системы счисления
- •Изображение числа в заданной системе счисления
- •Обратное преобразование
- •Итоги
- •Глава 48 Железная логика
- •Два взгляда на компьютерные «кирпичики»
- •Логические операции в регистрах
- •Сдвиги влево и вправо
- •Итоги
- •Глава 49 Сложные массивы
- •На поклон к Науке
- •Имперское строительство
- •Крестики-нолики
- •Итоги
- •А слабо?
- •Глава 50 Неспортивные рекорды (записи)
- •Кушать подано!
- •Записи
- •Второй тайм
- •Дополнительное время
- •Итоги
- •Глава 51 Указатели в море памяти
- •Погружение в оперативную память
- •«Планировка» памяти
- •Указатели, первое знакомство
- •Объявление указателей
- •Копирование указателей, пустой указатель
- •Сравнение и проверка указателей
- •Разыменование указателей
- •Нетипичный указатель
- •Примеры с указателями
- •Итоги
- •Глава 52 Динамические переменные
- •Аппетит является к обеду
- •Одолжите памяти немножко!
- •Выделение памяти
- •Освобождение памяти
- •Предупреждён – значит, вооружен
- •Итоги
- •Глава 53 Массив указателей
- •Базу данных – в кучу
- •Сортировка массива указателей
- •Итоги
- •А слабо?
- •Глава 54 Односвязные списки
- •Чудесное сочетание
- •Проблема курицы и яйца
- •Вяжем список
- •Распечатка списка
- •Поиск в несортированном списке
- •Сортированные списки
- •Поиск в сортированном списке
- •Итоги
- •Глава 55 Слова, слова, слова…
- •Частотный анализ текста
- •Слово за слово
- •Структура записи
- •Алгоритм
- •А слабо?
- •Глава 56 И снова очереди, и снова стеки…
- •Шутить изволите?
- •Танцуют все!
- •Итоги
- •Глава 57 Графомания
- •Видимое представление графа
- •Внутреннее представление графа
- •Ввод и вывод графа
- •Итоги
- •Глава 58 По графу шагом марш!
- •Империя номер два
- •Структура узла
- •В рассыпную!
- •Аты-баты
- •Итоги
- •Глава 59 Крупные проекты
- •О модулях и разделении труда
- •Модули
- •Дробление модуля – «смертельный» номер
- •Компиляция проекта
- •Инициализация модуля
- •Структура модуля
- •О совпадении имен
- •Сборочный цех
- •Фирменные библиотеки
- •Динамически загружаемые библиотеки (DLL)
- •Итоги
- •Глава 60 Мелкие хитрости
- •Включаемые файлы
- •Условная компиляция
- •Итоги
- •Глава 61 «Кубики» программиста (ООП)
- •Фокус-покус
- •Вместо паяльника
- •На трех китах
- •Инкапсуляция
- •Наследование
- •Приборостроение
- •Гражданское строительство
- •Динамические объекты
- •Полиморфизм
- •Сокрытие полей и методов
- •Итоги
- •Глава 62 Всё только начинается!
- •Крупицы мастерства
- •Программисты, на старт!
- •Приложение А Установка и настройка IDE Borland Pascal
- •Borland Pascal, состав дистрибутива
- •Borland Pascal
- •Установка
- •Организация рабочей папки
- •Создание и настройка ярлыка
- •Пробный запуск
- •Предварительная настройка
- •Русификация консольного окна
- •Turbo Pascal School Pak
- •Приложение Б Консольная программа в среде Delphi
- •Создание пустого консольного приложения
- •Настройка и сохранение консольного приложения
- •Русификация консольного приложения
- •Приложение В Особенности IDE Pascal ABCNet
- •Приложение Ж Директивы управления компиляцией
- •Приложение З Назначение пунктов меню
- •Приложение И Стандартная кодировка символов MS-DOS
- •Приложение К Некоторые встроенные процедуры и функции
- •Приложение М Пример олимпиадной задачи
- •Библиография
Глава 29 Читайте по-новому
Отдохнув на экскурсии, с новой силой набросимся на файлы, — ведь именно там хранятся наши данные. Научимся извлекать из файлов числа.
Полицейская база данных, версия 1
Одна из первых наших программ исполняла должность электронного часового, охранявшего секретный объект. Теперь поможем другой силовой структуре — дорожной полиции.
Долг автоинспектора — в числе прочего — поиск угнанных автомобилей. Работа нехитрая: заприметив подозрительный автомобиль, инспектор сверяет его номер со своей картотекой. И, если номер в картотеке найдется, принимает меры к задержанию автомобиля и поимке преступника. В отличие от часового, который помнит всего один пароль, полицейский роется в пухлой картотеке с тысячами номеров. В этом и состояла его главная трудность, пока не явились компьютерные
базы данных.
Базы данных (сокращенно БД) — кто не слышал о них? На ум приходят базы данных Пентагона, ЦРУ и налоговой инспекции. Да, эти чудовищные БД впечатляют! Впрочем, чтобы увидеть базу данных, не спешите потрошить Пентагон. Вот расписание поездов, программа телепередач или классный журнал,
— всё это простые базы данных. В конце концов, любая БД — это организованное хранилище данных, приспособленное для удобного поиска информации. Нам тоже по силам создать несложную полицейскую базу данных.
Соорудим такую базу с номерами угнанных автомобилей, и воспользуемся для этого текстовым файлом. Допустим, что номера автомобилей — это числа; тогда база данных — это файл с напечатанными в столбик номерами: каждая строка файла содержит один номер. Номера могут следовать в любом порядке, например:
123
325
234
11
Такой файл можно напечатать любым редактором текста, в том числе и встроенным в IDE. Мы так и поступим: создайте новый файл, впечатайте в него десяток-другой пришедших на ум номеров и сохраните в рабочей папке под именем «Police.txt». Окно с этим файлом пока не закрывайте, оно ещё пригодится.
Всё, база данных готова! Только не предлагайте полицейскому рыться в этом файле, — вместо благодарности вы услышите совсем другие слова. В довершение
191
Глава 29 Читайте по-новому
доброго дела напишем программу для поиска номера в этой базе. Такая программа должна работать как часовой, запрашивая у полицейского номер автомобиля и сообщая о том, содержится ли этот номер в БД. Признаком выхода из программы будет ввод нулевого номера.
Итак, приступим к программе P_29_1. Схема главной программы ясна из вышесказанного. Выносить заключение об автомобиле будет функция булевого типа, принимающая два параметра: файловую переменную, связанную с нашей БД, и номер искомого автомобиля. Если номер в базе данных обнаружится, функция вернет значение TRUE. Ввиду простоты алгоритма не буду рисовать блок-схему. Если чуете в себе силу, напишите программу сами, и, после некоторых мучений, сравните с тем, что показано ниже.
{ P_29_1 – Полицейская база данных, версия 1 }
function FindNumber(var aFile: text; aNumber: integer): boolean; var N: integer; { текущий номер в БД }
begin
FindNumber:= false; |
{ на случай, если файл пуст } |
||||
Reset(aFile); |
{ позицию чтения устанавливаем в начало файла } |
||||
N:=0; |
|
{ в начале цикла задаем несуществующий номер } |
|||
{ читаем номера из файла, пока НЕ конец файла И номер НЕ найден } |
|||||
while not Eof(aFile) and (N<>aNumber) do begin |
|
||||
Readln(aFile, N); |
|
|
|
||
FindNumber:= (N=aNumber); |
{ true, если номер нашелся } |
||||
end; |
|
|
|
|
|
end; |
|
|
|
|
|
var F: text; |
Num: integer; |
|
|
||
begin {----- Главная программа -----} |
|
|
|||
Assign(F, 'Police.txt'); |
|
|
|||
repeat |
|
|
|
|
|
Write('Укажите номер автомобиля: '); |
Readln(Num); |
||||
if FindNumber(F, Num) |
|
|
|||
|
then Writeln('Эта машина в розыске, хватайте его!') |
||||
|
else Writeln('Пропустите его'); |
|
until Num=0; { 0 – признак завершения программы} Close(F);
end.
Поясню некоторые моменты. В начале главной программы файловая переменная F связывается с файлом «Police.txt». Далее следует хорошо знакомая конструкция REPEAT—UNTIL с проверкой условия в конце цикла.
192
Глава 29 Читайте по-новому
Самое интересное скрыто внутри функции FindNumber (от Find — «искать», Number — «номер»). Туда передаются два параметра, один из которых — файловая переменная. Обратите внимание на способ её передачи: файловая переменная передается по ссылке (в заголовке указано слово VAR). И никак иначе файловую переменную не передают! Со временем узнаете причину, а пока просто запомните: файловые переменные передают внутрь процедур и функций только по ссылке! Следовательно, параметр aFile ссылается на глобальную переменную F.
А к чему здесь приставки «a» перед именами параметров: aFile, aNumber? Или это тоже правило языка? Нет, друзья, это всего лишь уловка программистов, которую полезно перенять. Чем сложнее будут ваши программы, тем гуще будут заселены разного рода переменными и параметрами. Во избежание путаницы лучше учредить разумную систему обозначений. Большинство программистов используют для систематизации имен так называемые префиксы или приставки. Например, для параметров (аргументов) процедур и функций применяют префикс «a» (от слова «argument»). Помеченные таким образом параметры уже не спутаешь с локальными или глобальными переменными.
Теперь заглянем внутрь функции FindNumber. В первой строке результату функции присваивается значение FALSE. И это оправдано, поскольку значение функции обязательно должно быть определено, а в случае, если файл БД окажется пустым, этого не случится, поскольку следующий далее цикл WHILE не будет выполняться.
Поиск номера должен начинаться с начала файла. Оператор Reset внутри функции как раз и возвращает позицию чтения на линию старта. Будьте спокойны
— файл от этого не пострадает, открывать его для чтения можно без ограничений!
Теперь взгляните на условие цикла WHILE, — оно чуть сложнее тех, к которым мы привыкли.
while not Eof(aFile) and (N<>aNumber)
Наряду с признаком конца файла проверяется и условие несовпадения искомого номера с номером, прочитанным из файла. Значит, цикл будет продолжаться, пока НЕ достигнут конец файла И НЕ найден искомый номер.
Внутри цикла находим непривычный оператор присваивания.
FindNumber:= (N=aNumber); |
{ true, если номер нашелся } |
Левая его часть — это идентификатор функции, а правая (в скобках) — оператор сравнения двух чисел. Оператор сравнения дает булев результат, равный TRUE, если числа совпадают. Скобки в правой части здесь не нужны, но я поставил их для наглядности. Приведенный выше оператор можно было бы заменить таким.
193
Глава 29 Читайте по-новому
if N=aNumber
then FindNumber:= true
else FindNumber:= false;
Но, согласитесь, первый вариант наглядней и короче.
Итак, прежде чем двинуться дальше, не поленитесь проверить эту программу.
Полицейская база данных, версия 2
Теперь слегка изменим расположение чисел в файле «Police.txt». Вместо одного числа в строке, напечатайте в каждой по нескольку чисел, разделив их одним или несколькими пробелами, например:
123 234 325
223 240
845 431 205
Подобное расположение данных вполне обычно, взгляните хотя бы в классный журнал, где в одной строке проставлен ряд оценок. Мы, программисты, должны извлекать данные даже из таких файлов.
Переключитесь в окно нашей базы данных «Police.txt» и внесите необходимые изменения. Сохранить файл не забыли? Теперь запустите программу и проверьте её на номерах из этого файла. При должном внимании вы обнаружите, что программа правильно находит только числа, начинающие строку, например 123, 223 и 845. Все последующие номера в строке программа не замечает, хотя и аварийных сообщений не выдает. В чем же дело?
Причина — в процедуре Readln. До сих пор мы пользовались ею для чтения строк и горя не знали. Но числа — иное дело. Приглашаю вас мысленно проследить за позицией чтения в ходе просмотра нашей БД (рис. 66). Невидимые признаки конца строки обозначены на рисунке условными символами Eoln (это пара символов с кодами 13 и 10).
194
Глава 29 Читайте по-новому
Reset |
123 |
234 |
325 |
Eoln |
|
||||
Readln |
223 |
240 |
Eoln |
|
Readln |
845 |
431 |
205 |
Eoln |
Рис. 66 – Продвижение позиции чтения процедурой Readln
После того, как Reset установит позицию чтения в начало файла, процедура Readln прочитает первое число. Чтение идет цифра за цифрой, пока не встретится любой символ, отличный от неё, например, пробел или конец строки. Проглотив таким образом первое число, процедура Readln продвинет позицию чтения в начало следующей строки, пропуская при этом всё, что расположено до конца текущей. Вот в чем дело! Не зря к названию процедуры прилепился суффикс «LN» (сокращенное от Line — «строка»). Источник проблемы ясен: процедура Readln не подходит для чтения нескольких чисел в строке. Где же выход?
Спокойно, друзья, в Паскале заготовлено всё! Познакомьтесь с процедурой Read (без суффикса), которая почти не отличается от своей «сестренки» — принимает те же параметры и читает те же данные. Но при этом самовольно не продвигает позицию чтения в начало следующей строки. А нам того и нужно! Продвижение позиции чтения процедурой Read показано на рис. 67.
Read |
Read |
Reset |
|
123 |
234 |
223 |
240 |
Read |
|
845 |
431 |
325 Eoln
Eoln
205 Eoln
Рис. 67 – Продвижение позиции чтения процедурой Read
После чтения каждого числа позиция продвигается за это число и остаётся там. Следующий вызов процедуры прочитает очередное число в этой же строке и так далее, пока не будет достигнут конец строки. А потом? Потом позиция
195