3 587 + 954 = 1541
4 629 + 916 = 1545
5 691 + 876 = 1567
6 694 + 872 = 1566
7 749 + 845 = 1594
8 751 + 800 = 1551
Здесь самый легкий и самый тяжелый слитки отличаются почти вдвое: 506 и 975 граммов. Но пары слитков, доставшихся пиратам, отличаются по весу незначительно.
Возвращение на футбольное полеЗакаленные морскими приключениями, вернемся к сортировке футбольных клубов (задача поставлена в главе 39, помните?). Что мы будем сортировать? Набранные очки? Да, но их надо как-то привязать к названиям команд.
Поступим так. Объявим два массива: один (числовой) – для набранных очков, другой (строковый) – для названий клубов. При вводе данных элементы двух массивов будут соответствовать друг другу, поскольку имена команд и набранные ими очки вводятся одновременно. Затем, в ходе сортировки, переставляя элементы с очками, будем менять местами и соответствующие им элементы с названиями команд. Так имена команд последуют за очками, заработанными командами. Все это потребует небольших переделок в процедуре сортировки.
Впрочем, потребуется ещё одно мелкое изменение. Если при сортировке золотых слитков мы добивались возрастающего порядка, то теперь нужен противоположный, убывающий порядок сортировки. Как его добиться? Очень просто: изменим условие сравнения соседних элементов на противоположное. Вот собственно и все, осталось лишь показать программу «P_41_3».
{P_41_3 – Футбольный чемпионат }
const CSize = 16; { количество команд }
{ объявление типов для массивов }
type TAces = array [1..CSize] of integer; { тип для очков }
TNames = array [1..CSize] of string; { тип для названий }
var Aces : TAces; { набранные очки }
Names: TNames; { названия команд }
{ Процедура "пузырьковой" сортировки очков с именами команд }
procedure BubbleSort2(var arg1: TAces; var arg2: TNames);
var i, j, t: Integer;
s: string;
begin
for i:= 1 to CSize-1 do { внешний цикл }
for j:= 1 to CSize-i do { внутренний цикл }
{ если текущий элемент меньше следующего …}
if arg1[j] < arg1[j+1] then begin
{ то меняем местами соседние элементы }
t:= arg1[j]; { временно запоминаем }
arg1[j]:= arg1[j+1]; { следующий -> в текущий }
arg1[j+1]:= t; { текущий -> в следующий }
{ меняем местами и названия команд }
s:= arg2[j]; { временно запоминаем }
arg2[j]:= arg2[j+1]; { следующий -> в текущий }
arg2[j+1]:= s; { текущий -> в следующий }
end;
end;
var i: integer;
begin { главная программа }
{ Вводим названия команд и набранные очки }
for i:=1 to CSize do begin
Write('Название команды: '); Readln(Names[i]);
Write('Набранные очки: '); Readln(Aces[i]);
end;
BubbleSort2(Aces, Names); { сортируем }
Writeln('Итоги чемпионата:');
Writeln('Место Команда Очки');
for i:=1 to CSize do
Writeln(i:3,' ':3, Names[i], Aces[i]:20-Length(Names[i]));
Readln;
end.
Спецификатор ширины поля в операторе печати задан выражением.
20 – Length(Names[i])
Здесь перед колонкой с очками будет тем больше пробелов, чем короче название команды, – так выравниваются колонки таблицы.
Для проверки программы я ввел наобум имена четырех команд нашего чемпионата и очки, якобы заработанные ими (количество команд CSize установил равным 4), и вот что у меня вышло.
Итоги чемпионата:
Место Команда Очки
1 Локомотив 55
2 Крылья Советов 54
3 Спартак 47
4 Зенит 43
Болельщики вправе оспорить результат, но я им доволен.
Итоги• Расположение данных в порядке возрастания или убывания называется сортировкой.
• Простейший алгоритм сортировки массива – «пузырьковая» сортировка. Она состоит в сравнении и перестановке соседних элементов массива, при этом организуются два вложенных цикла.
А слабо?А) Напишите программу для сортировки фамилий учеников в алфавитном порядке (фамилии берутся из файла). Программа должна сортировать их как по возрастанию, так и по убыванию фамилий, – на выбор пользователя.
Б) Придумайте самый несправедливый способ пиратской дележки по два слитка и напишите программу для неё.
В) Напишите программу для дележки случайным образом (как это собирались сделать пираты). Насколько отличаются ваши результаты от справедливого способа?
Г) Напишите функцию, проверяющую, упорядочен ли числовой массив. Функция должна вернуть TRUE, если массив упорядочен по возрастанию. Массив внутрь функции передайте параметром по ссылке.
Глава 42Кто ищет, тот всегда найдет
Все кругом ищут что-то: Карабас-Барабас – золотой ключик, Лиса с Котом – дураков, а Буратино – Страну Дураков. И я ищу: то ключи в карманах, то тапочки под диваном. А сколько всего таится в Интернете! Благо, искать информацию там помогают компьютеры.
Где эта улица, где этот дом?В 40-й главе мы смастерили программу для поиска угнанных автомобилей. Испытаем её вон на той легковушке. Вводим номер машины и… оп! Вот так удача! Автомобильчик-то в розыске, – надо вернуть его владельцу. Однако, кто он? Где живет? А телефончик не подскажете? К сожалению, в нашей базе данных этих сведений нет, – её следует дополнить.
Добавим в программу поиска автомобилей массив строк, где будем хранить сведения о владельце: его имя, фамилию и телефон.
const CNumbers = 100; { размер массивов }
type TNumbers = array[1..CNumbers] of integer;
TNames = array[1..CNumbers] of string;
var Numbers : TNumbers; { массив номеров автомобилей }
Names : TNames; { массив сведений о владельце }
Здесь добавлен массив Names (имена), содержащий столько же строк, сколько номеров в базе данных. Эти строки соответствуют элементам массива номеров Numbers. Так, если элемент Numbers[7] содержит число 123, а элемент Names[7] – строку «Горбунков С.С., тел. 11-22-33», то значит, гражданин Горбунков владеет автомобилем с номером 123.
Что связывает массивы Names и Numbers? Ответ очевиден – общий индекс. Определив индекс автомобиля в массиве номеров, мы получим доступ и к сведениям о его владельце в строковом массиве.
Последовательный поискНапомню, что в полицейской базе данных из 40-й главы заголовок функции поиска был таким.
function FindNumber(aNum: integer): boolean;
Функция FindNumber выясняет, существует ли искомый номер в массиве Numbers, то есть она дает булев результат. Теперь этого мало, – хочется получить индекс элемента, где хранится искомый номер. А если такого номера в массиве нет? Пусть тогда функция вернет некоторое условное значение, например, минус единицу.
С учетом этих пожеланий, напишем новую функцию поиска и дадим ей имя FindSeq (от слов Find – «искать», Sequence – «последовательно»).
{ Функция поиска в массиве Numbers позиции числа aNum }
function FindSeq (aNum: integer): integer;
var i: integer;
begin
FindSeq:= -1; { если не найдем, то результат будет -1 }
for i:=1 to Fact do
if aNum=Numbers[i] then begin
FindSeq:= i; { нашли, возвращаем индекс }