Поиск по базе по вторичным ключам.
Нужно сделать возможность обращаться к данным из базы не только по первичному ключу, но и по дополнительным ключам, заданным пользователем. Индекс создается по запросу пользователя. Пользователь указывает имя индекса, исходную таблицу и номер колонки, по которой нужно построить индекс. После этого создается объект, реализующий интерфейс Index, который представляет из себя сокращение Table. С помощью этого объекта можно работать с индексом.
Прообраз интерфейса Table - интерфейс Index.
Ваш TableProvider
, который создается с помощью TableProviderFactory
, теперь должен также реализовывать
интерфейс IndexProvider, а именно, его методы
Index createIndex(Table table, int column, String name)
и Index getIndex(String name)
.
"Протаскивать" новый интерфейс в декларации не нужно.
Индекс нужно хранить в отдельной директории, рядом с таблицами. Имена индексов и таблиц не должны совпадать - т.е. имена являются уникальными идентификаторами.
Аналогично, как для Storeable-таблицы необходим файл с описанием схемы, для индекса нужен файл-ссылка на таблицу. Он должен состоять из одной строки, в которой два поля, разделенных через пробел - имя таблицы и номер колонки, по которой построен индекс.
Пример:
IndexedTable 2
Колонка для индекса не должна содержать повторяющихся элементов, а также null-элементов. Это нужно проверить при создании индекса и каждый раз проверять при вставке в таблицу.
Индекс должен существовать вне транзакций, только на закоммиченных данных.
- Лучше всего в индексе хранить отображение из вторичного ключа в первичный.
- Поскольку формат хранения индекса не задан, можно использовать любой. Наиболее простым будет хранить индекс в нескольких .tsv-файлах. Удобно будет расположить их таким же образом, как и файлы для поиска по первичному ключа.
- Read-only индекс, перестраиваемый внутри критической секции при коммите, избавит вас от проблем с многопоточным доступом.
- Команды шелла для работы с индексом не нужны.