Глава 4. Поиск.
Глава 4. Поиск.
Поиск - это действие, заключающееся в просмотре набора элементов и выделении из этого набора интересующего элемента. Наверное, все вы знакомы с одной из функций поиска - Pos из модуля SysUtils, которая предназначена для поиска подстроки в строке.
Эта и следующая главы, посвященные поиску, довольно-таки тесно связаны между собой. Часто поиск элемента приходится осуществлять в уже отсортированном контейнере. И если контейнер отсортирован, можно воспользоваться эффективным алгоритмом для поиска позиции вставки нового элемента, чтобы и после вставки контейнер оказался отсортированным. Тем не менее, поиск не ограничивается просмотром отсортированных списков. Мы, помимо прочих, рассмотрим простейший тип поиска - алгоритмы, которые кажутся почти очевидными и не заслуживают специального названия.
Кроме того, настоящая глава служит мостом между простыми фундаментальными контейнерами, массивами и связными списками, и более сложными, например, бинарными деревьями, списками пропусков и хеш-таблицами. Эффективный поиск зависит от сложности контейнера, в котором находятся элементы, поэтому мы приводим алгоритмы как для массивов, так и для связных списков. В последующих главах при рассмотрении более сложных контейнеров мы всегда будем говорить об оптимальной стратегии поиска для обсуждаемых структур данных.
Процедуры сравнения
Само действие поиска элемента в наборе элементов требует возможности отличать элементы друг от друга. Если мы не можем различить два элемента, то не имеет смысла искать один из таких элементов. Таким образом, первая трудность, которую нам потребуется преодолеть, - это сравнение двух элементов, находящихся в одном наборе. Существует два типа сравнения. Первый из них предназначен для несортированных списков элементов, когда все, что нам нужно знать, так это равны ли два элемента. Второй тип используется в отсортированных списках элементов, когда можно добиться повышения эффективности поиска, если имеется возможность определить отношение одного элемента к другому (меньше, равен или больше). (Фактически, операция сравнения определяет, в каком порядке элементы находятся в списке. При поиске в отсортированном списке необходимо выполнять то же самое сравнение, на основе которого был построен список.)
Очевидно, что если элементы принадлежат к целочисленному типу, операция сравнения не представляет никаких трудностей: все мы можем взять два целых числа и определить, отличаются они или нет. В случае строк сравнение усложняется. Можно выполнять сравнение, чувствительное к регистру (т.е. строчные символы будут отличаться от прописных), и сравнение, нечувствительное к регистру (т.е. строчные символы не будут отличаться от прописных), сравнение по локальным таблицам символов (сравнение на основе алгоритмов, специфических для определенной страны или языка) и т.д. Тип set в Delphi, несмотря на то, что он позволяет сравнивать два набора, все же не имеет четко определенного способа определения того, что один набор больше другого (фактически выражение "один набор больше другого" не имеет смысла, если речь не идет о количестве элементов). А что касается объектов, то здесь даже нет метода, который бы позволил сказать, что объект A равен или не равен объекту B (за исключением сравнения указателей на объекты).
Лучше всего на данном этапе рассматривать процедуру сравнения в виде "черного ящика" - функции с четко определенным интерфейсом или синтаксисом, которая в качестве входного параметра принимает два элемента и возвращает результат сравнения - первый элемент меньше второго, первый элемент равен второму или первый элемент больше второго. Для тех типов элементов, которые не имеют определенного порядка (т.е. даже если известно, что два элемента не равны, мы не можем определить, меньше элемент A элемента B или больше), нужно предусмотреть, чтобы функция сравнения возвращала значение, которое трактуется как "не равно".
В книге все функции сравнения принадлежат к типу TtdCompareFunc (этот тип объявлен в файле TDBasics.pas, который можно найти на Web-сайте издательства, в разделе материалов; там же находятся и примеры функций сравнения):
Листинг 4.1. Прототип функции TtdCompareFunc
type
TtdCompareFunc = function(aData1, aData2 : pointer) : integer;
Другими словами, функция сравнения в качестве входных параметров принимает два указателя и возвращает целочисленное значение. Возвращаемое значение будет равно 0, если два сравниваемых элемента равны, меньше нуля, если первый элемент меньше второго, и больше нуля, если первый элемент больше второго. Тип параметров aData1 и aData2 определяет сама функция, и она же решает, что делать с переданными данными: привести к определенному классу или просто к типу, который не является указателем.
Приведем пример функции сравнения, которая предполагает, что входные параметры принадлежат к типу longint, а не представляют собой указатели. (Будем считать, что значение sizeof(longint) равно sizeof(pointer). На сегодняшний день это справедливо для всех версий Delphi.)
Листинг 4.2. Функция TDCompareLongint
function TDCompareLongint(aData1, aData2 : pointer) : integer;
var
L1 : longint absolute aData1;
L2 : longint absolute aData2;
begin
if (L1 < L2) then
Result := -1
else if (L1 = L2) then
Result := 0
else
Result := 1
end;
Перед тем как в ужасе сказать, что вы бы никогда не вызвали такую функцию сравнения двух значений типа longint, обратите внимание, что этого и не требуется. Приведенная функция предназначена для использования структурами данных, которые принимают элементы в виде указателей (например, список TtdSingleLinkList или стандартный массив TList), и подпрограммами, которые используют такие структуры данных. Если вы разрабатываете функцию поиска, исходя из главных принципов, имеет смысл написать и процедуру сравнения. Остается надеяться, что все мы сможем написать функцию для сравнения двух целых чисел.
Давайте рассмотрим пример функции TDCompareNullStr, предназначенной для сравнения двух строк, завершающихся нулем, не привязываясь к алфавиту определенной страны:
Листинг 4.3. Функция TDCompareNullStr
function TDCompareNullStr(aData1, aData2 : pointer) : integer;
begin
Result := StrComp(PAnsiChar(aData1), PAnsiChar(aData2));
end;
(В Delphi1 в модуле TDBasics объявлено, что тип PAnsiChar соответствует типу PChar.) К счастью, для данного примера стандартная функция StrComp возвращает значение того же типа, что и требуется для нашей функции сравнения.
В качестве последнего примера приведем функцию TDCompareNullStrAnsi, предназначенную для сравнения двух строк, завершающихся нулем, с учетом локальных таблиц символов:
Листинг 4.4. Функция TDCompareNullStrAnsi
function TDCompareNullStrAnsi(aData1, aData2 : pointer) : integer;
begin
{$IFDEF Delphi1}
Result := lstrcmp(PAnsiChar(aData1), PAnsiChar(aData2));
{$ENDIF}
{$IFDEF Delphi2Plus}
Result := CompareString(LOCALE_USER_DEFAULT, 0,
PAnsiChar(aData1), -1,
PAnsiChar(aData2), -1) - 2;
{$ENDIF}
{$IFDEF Kylix1Plus}
Result := strcoll(PAnsiChar(aData1), PAnsiChar(aData2));
{$ENDIF}
end;
В приведенной функции для Delphi1 и 32-разрядных версий Delphi используются разные коды. Кроме того, обратите внимание, что функция lstrcmp возвращает значения в том виде, который нужен нам. К сожалению, функция CompareString этого не делает. Она возвращает 1, если первая строка меньше второй, 2, если строки равны, и 3, если первая строка больше второй. Поэтому для получения требуемого значения необходимо просто вычесть 2 из результата, возвращаемого функцией CompareString. В Kylix для сравнения строк нужно воспользоваться функцией strcoll из модуля Libc.
Более 800 000 книг и аудиокниг! 📚
Получи 2 месяца Литрес Подписки в подарок и наслаждайся неограниченным чтением
ПОЛУЧИТЬ ПОДАРОКЧитайте также
Глава 2 Вертикальный поиск
Глава 2 Вертикальный поиск Важным направлением развития современного интернет-поиска стало появление большого количества специализированных поисковиков, предназначенных для углубленного поиска определенного тематического контента. Такие интернет-машины часто
Глава 7 Поиск изображений
Глава 7 Поиск изображений Интернет-поиск уже давно не ограничивается только текстовыми документами. Пожалуй, следующий по популярности тип контента – изображения. Сейчас можно насчитать три основных направления в развитии технологий интернет-поиска изображений – это
Глава 8 Поиск видео
Глава 8 Поиск видео Интернет-поиск видеофайлов, как и поиск изображений, можно вести различными способами. Значительная часть видеоконтента в современной. Сети сохраняется на многочисленных видеохостингах, наиболее крупным и известным из которых остается YouTube. Среди
Глава 9 Поиск «скрытого» контента
Глава 9 Поиск «скрытого» контента Контент глобальных сетей никогда не ограничивался общедоступными сайтами и ресурсами. Значительное количество ресурсов были и остаются в большей или меньшей степени закрытыми. Причины такого ограничения доступа могут быть самыми
Глава 10 Поиск для Web 3.0
Глава 10 Поиск для Web 3.0 Технологии «семантического веба» – главного претендента на роль следующего поколения развития. Сети, которое уже окрестили Web 3.0, неторопливо, но верно обосновываются на все большем количестве интернет-сервисов. Появление новых проектов связано с
Глава 5 Поиск в Интернете
Глава 5 Поиск в Интернете • Поисковые серверы. Некоторые правила поиска• Поисковые запросы: подробно• Поиск рисунков• Поиск музыки и видео• Поиск по FTP-серверам• Альтернативные средства поиска• «Википедия» – живая энциклопедия и ее альтернативыПроблема поиска во
Глава 4 Поиск информации
Глава 4 Поиск информации – Поисковые системы.– Каталоги.– Помощь пользователей Интернета в поискеТрое из четырех пользователей, отвечая на вопрос: «Для чего вы используете Интернет?», называют поиск информации. И это не мудрено – в Сети, без преувеличения, есть
Глава 16 Поиск информации на узле SharePoint
Глава 16 Поиск информации на узле SharePoint В этой главе вы научитесь:• использовать поисковую систему;• выполнять простой поисковый запрос;• выполнять простой поисковый запрос.Для поиска информации на узлах службы Windows SharePoint доступно два основных метода. Первый:
Глава 1 Поиск (Найдется всё!)
Глава 1 Поиск (Найдется всё!) Главная задача информационно-поисковой системы — это поиск информации, релевантной информационным потребностям пользователя. Слово релевантность означает соответствие между желаемой и действительно получаемой информацией. Релевантность
Глава 10 Поиск информации в Интернете
Глава 10 Поиск информации в Интернете • Поиск в Интернете: общие понятия• Виртуальные библиотеки• Форматы электронных книг• Поиск рефератов• Поиск в библиотекахДля многих людей на сегодняшний день Интернет стал обязательным источником информации. Если раньше при
Глава 4. Поиск классов
Глава 4. Поиск классов Что такое объектОбъект (object) — это некая сущность реального мира или концептуальная сущность. Объект может быть чем-то конкретным, например грузовик Джо или мой компьютер, или концептуальным, как, например, химический процесс, банковская операция,
Глава 3 Поиск в Интернете
Глава 3 Поиск в Интернете Поисковые серверы. Некоторые правила поискаПоисковые запросы: подробноАльтернативные средства поискаПоиск рисунков в ИнтернетеПоиск музыки и видеоПоиск по FTP-серверамПроблема поиска во Всемирной паутине не в том, что информации мало, а в том,
Глава 4. Поиск.
Глава 4. Поиск. Поиск - это действие, заключающееся в просмотре набора элементов и выделении из этого набора интересующего элемента. Наверное, все вы знакомы с одной из функций поиска - Pos из модуля SysUtils, которая предназначена для поиска подстроки в строке.Эта и следующая
Глава 9 Поиск информации в Интернете
Глава 9 Поиск информации в Интернете Для очень многих людей Интернет стал на сегодняшний день обязательным источником информации. Если раньше при написании работы, да и просто при необходимости что-то узнать, пользовались справочниками, каталогами, книгами и журналами,
Глава 2 Поиск информации в Интернете
Глава 2 Поиск информации в Интернете Любая область человеческой деятельности в том или ином виде нашла свое отражение в Интернете. Важнейшая задача — уметь быстро найти то, что интересует именно вас. Сейчас проводятся международные соревнования по поиску информации.
Глава 5 Поиск различий
Глава 5 Поиск различий В этой главе обсуждаются следующие темы: • Суть поиска различий • Исследование инсрументария поиска различий • Поиск неисправностей · Резюме · Конспект · Часто задаваемые вопросы