Мир InterBase. Архитектура, администрирование и разработка приложений баз данных в InterBase/FireBird/Yaffil - А Ковязин
Шрифт:
Интервал:
Закладка:
В зависимости от характера данных упаковка может оказаться нецелесообразной. Наибольший эффект достигается при сжатии "хвостов" из пробелов длинных текстовых строк (типы данных CHAR и VARCHAR), в то время как короткие нетекстовые данные практически несжимаемы.
Для управления сжатием в Yaffil введен параметр конфигурации SQZ_BLOCK. Этот параметр определяет минимальный размер блока строки таблицы (в байтах), начиная с которого будет производиться сжатие. Блоки строки таблиц менее указанного размера хранятся в исходном виде. С увеличением параметра объем базы данных возрастает за счет сокращения затрат времени процессора на упаковку. В то же время увеличение количества данных больше нагружает дисковую подсистему. В зависимости от характера данных (главным образом количества текстовых полей в таблицах) и определенных параметров процессора и дисков системы существует некоторое оптимальное значение SQZ_BLOCK, обеспечивающее максимальную производительность. Алгоритм упаковки, реализованный в Yaffil, дополнительно выравнивает начало и размер сжатого блока на границу машинного слова.
Ускоренная работа с индексами
Гораздо быстрее работают операции поиска по индексам (часто используемые в соединениях), а также построения индексов. Это достигнуто за счет тщательной оптимизации кода индексирования.
Улучшенная стратегия вычисления предиката IN и условий, объединенных по OR
По сравнению с InterBase и другими клонами, Yaffil выполняет предикат IN гораздо более эффективно. При этом используется только одно построение битовой карты для индекса, независимо от числа параметров. В других клонах InterBase получим значительное замедление при большом числе параметров, (особенно если IN не ограничивает основной объем выборки), несмотря на одинаковый план исполнения запроса. То же самое произойдет и для условия вида OR:
select * from Т where Fl = .. or F2 = ... or F2
Ускоренное обновление данных
Наибольший выигрыш в скорости при использовании Yaffil наблюдается при обновлении данных.
Переработаны алгоритмы, связанные с управлением деревом "грязных страниц" буферного кэша, в результате чего устранено замедление при массивных обновлениях данных в рамках одной транзакции. Ликвидирована известная проблема InterBase, при которой задание числа буферов больше некоторого предела (около 10 000) приводит не к увеличению скорости, а совсем наоборот, при этом возможны даже зависания (известная проблема "10 000 буферов").
Устранена деградация скорости при обновлении большого числа рядов данных, а 1аюке при откате большого числа изменений. Быстрее выполняется массовая вставка данных также за счет оптимизации кода.
Уменьшение времени, необходимого для резервного копирования и восстановления
В InterBase отсутствует возможность инкрементального резервного копирования, при этом сам процесс backup/restore из-за архитектурных особенностей проходит медленнее по сравнению с серверами СУБД, где запись копии происходит постранично. Резервное копирование большой базы может занимать несколько часов, при этом хоть и возможна работа пользователей, но время отклика ухудшается.
На Yaffil резервное копирование и восстановление происходит в несколько раз быстрее, особенно заметно это на больших базах данных (отсутствует деградация скорости копирования со временем).
Индексы по выражениям
Индексы по выражениям (Expression Indexes) используются в тех случаях, ко- |да необходимо обеспечить быстрый поиск или сортировку по значениям, вычисляемым на основе полей таблицы. Необходимый индекс определяется следующим образом:
CREATE [UNIQUE] [ASC[ENDING] | DESC[ENDING]]
INDEX index ON table COMPUTED BY (expression)
где index - имя индекса, expression - выражение, построенное на основе полей таблицы. В выражении можно использовать арифметические операции, встроенные функции и UDF. Во время оптимизации запросов, если выражение совпадает с выражением, указанным в условии WHERE или в условии соединения, будет использован индекс.
Например, необходимо сделать выборку записей, имеющих поле типа дата, для определенного месяца по всем годам (на примере базы данных Employee из комплекта поставки InterBase 6):
CREATE INDEX employeejhire_date_month_idx ON employee COMPUTED
BY (EXTRACT(MONTH FROM hire_date) ) ;
Попробуем выполнить запрос и посмотрим на выбранный оптимизатором план:
SELECT * FROM employee
WHERE EXTRACT(MONTH FROM hire_date) = 1
PLAN (EMPLOYEE INDEX (EMPLOYEE_HIRE_DATE_MONTH_IDX))
Вычисляемое выражение должно полностью определяться значениями полей таблицы, индекс на основе, например, функции CURRENT_TiMESTAMP, скорее всего, будет бесполезен, хотя Yaffil не запрещает использование подобных выражений. В вычисляемых выражениях нельзя использовать подзапросы. Очень интересные возможности появляются при использовании User-Defined Functions (UDF) в вычисляемых выражениях, с их помощью можно выполнять эффективный поиск по практически любому условию.
Уменьшение размера, занимаемого индексами
Индексы, построенные по текстовым полям с национальным порядком сортировки, занимают в среднем на одну треть меньше места на диске по сравнению с Interbase.
Выражения в значениях по умолчанию для доменов
Yaffil позволяет использовать сложные выражения для значений по умолчанию в доменах:
CREATE DOMAIN NEW_DOMAIN AS INTEGER DEFAULT (GEN_ID(NEW_GENERATOR, 1))
Подобная возможность позволяет не писать дополнительные триггера для выполнения схожих действий.
Удобная операция объединения строк
Yaffil позволяет объединять строки с использованием оператора "||" при превышении размера результата максимальной длины строки. При этом результирующая строка будет иметь максимально допустимый сервером размер, а ошибка переполнения возникает, только если действительные данные пользователя не могут быть размещены в результирующей строке. Такое поведение оператора "||" соответствует привычному поведению обычных арифметических операторов над числами.
В качестве примера приведем вариант с объединением двух полей:
CREATE TABLE Т(VI VARCHAR(20000), V2 VARCHAR(20000)}.
При попытке написать VI || V2 Interbase/Firebird выдадут ошибку переполнения еще на этапе компиляции. Сервер Yaffil в качестве результата сформирует строку VARCHAR(32765). Ошибка переполнения возникнет, только если количество символов объединения VI и V2, исключая концевые пробелы, превысит 32765.
Расширенные возможности указания пользовательских планов
Не всегда встроенный оптимизатор может выбрать оптимальный план. Причиной этого может быть отсутствие подробной статистики по индексам и полям, без которой трудно оценить стоимость выполнения варианта или слишком большое число вариантов соединений. В таких случаях приходится применять явные планы в запросах.
Yaffil расширяет возможности использования явных планов, тем самым предоставляя возможность дальнейшего ускорения работы приложений.
В Yaffil появилась возможность указывать явные планы в некурсорных операторах обновления данных, таких, как UPDATE и DELETE. Дополнительно ним можно добиться обновления или удаления строк данных в заданном порядке указав использование индекса в условии ORDER.
Как известно, в InterBase не разрешается использование явных планов в тексте триггеров. Yaffil снимает это ограничение.
Имена индексов ограничений
Использование явных планов в Yaffil в триггерах и процедурах существенно упрощается благодаря возможности именования индексов, автоматически создаваемых сервером для ограничений первичных, внешних ключей и ограничений уникальности. В версиях InterBase такие индексы приобретают системные имена в формате RDBSPRIMARYX для индексов первичных ключей, RDB$FOREIGNX для индексов внешних ключей и RDB$X для индексов ограничений уникальности. X обозначает номер индекса данного типа по порядку с момента создания базы данных (или восстановления из резервной копии). Так как эти номера могут измениться при следующем восстановлении базы данных, фиксировать такие индексы в плане становится опасным. Возникает тупиковая ситуация: автоматический план неэффективен, явный план записать нельзя. Разработчикам приходится создавать собственные индексы, целиком дублирующие системные. Однако появление новых индексов на таблице влечет к увеличению дискового пространства, занимаемого базой, замедлению операций обновления, кроме того повышению вероятности выбора оптимизатором неверного плана из-за увеличения числа вариантов соединений таблиц.
В Yaffil индексы для ограничений могут принимать имена соответствующих ограничений.
Нужное поведение включается параметром CONSTRAINT_INDEX_NAME в конфигурационном файле. Например:
SQL> create table T (id into not null, constraint PK_T primary
key (id));
SQL> show index;
PK_T UNIQUE INDEX ON Т(ID)
Улучшенное время отклика для версии SuperServer
В серверах Bolrand InterBase версии ниже 7.0, использующих архитектуру SuperServer, одновременное обслуживание нескольких клиентов реализовано по схеме многопоточного сервера. Однако переключение процессора между потоками (диспетчеризация) происходит не по требованию операционной системы, а в моменты времени, выбираемые активным потоком "добровольно". Такая схема очень похожа на реализацию многозадачности в Windows 3.1 и называется невытесняющей многозадачностью.