Android: используйте UUID в качестве первичного ключа в SQLite
Мое приложение должно синхронизироваться с другими пользователями приложений (там есть собственные устройства). Я также хочу поддерживать автономное редактирование, которое синхронизируется с другими пользователями совместной работы, когда пользователь подключается к Интернету.
Таким образом, Пользователь А изменяет (пока он в автономном режиме) некоторые данные (в словах, которые он обновлял в базе данных) или добавлял новые записи в базу данных. Когда пользователь A подключается к Интернету, все изменения и новые записи доставляются другим пользователям. Таким образом, пользователь B получит изменения/обновления и может вставлять/обновлять их в базу данных локальных устройств пользователя.
Но мне нужно убедиться, что идентификаторы записей базы данных уникальны по всей системе. Поэтому мне нужно использовать что-то вроде UUID.
Мой вопрос: Неплохо ли использовать UUID (String/Varchar) в качестве первичного ключа в таблице базы данных android sqlite вместо целого числа, которое будет автоматически увеличиваться?
Я думаю, что в качестве первичного ключа будут проблемы с производительностью, используя строки (UUID имеет 36 символов).
Я думаю, что индексирование uuids вместо целых чисел занимает больше времени (сравнение строки и сравнения целых чисел). Я также предполагаю, что когда Im, использующий UUID, каждый раз, когда была добавлена запись/запись базы данных, база данных должна переиндексировать столбец первичного ключа, так как индекс первичного ключа больше не отсортирован (что было бы, когда я буду использовать целочисленный автоматический прирост первичного ключа, поскольку каждая последующая запись добавляется в конце, потому что новый автоматически увеличиваемый первичный ключ всегда является наибольшим числом, поэтому индекс будет автоматически отсортирован в порядке). То, что мне также нужно сделать, - это СОЕДИНЕНИЯ свыше 2 - 3 таблиц. Я также предполагаю, что сравнение строк в JOINS вместо целых будет замедлять запрос базы данных.
Однако я не вижу никакой другой возможности для реализации такой совместной системы синхронизации, поэтому я должен использовать UUID, правильно?
Другой возможностью было бы использовать первичный ключ с автоматическим добавлением целых чисел и использовать второй uuid столбца. Поэтому для работы с локальным устройством пользователей я бы использовал этот первичный ключ (integer) для JOINS и т.д., В то время как я использовал бы столбец uuid для синхронизации с другими пользователями.
Что вы, ребята, думаете об этом подходе или, по вашему мнению, много работаете, так как вы не ожидаете значительную проблему с производительностью, используя UUID напрямую в качестве первичного ключа?
Любые другие предложения?
Ответы
Ответ 1
Неплохо ли использовать UUID (String/Varchar) в качестве первичного ключа в таблице базы данных android sqlite вместо целого числа, которое будет автоматически увеличиваться?
Единственная непредсказуемая проблема, о которой я могу думать, заключается в том, что вы не сможете использовать CursorAdapter
и ее подклассы для отображения результатов запросов в этой таблице. CursorAdapter
требуется уникальный целочисленный столбец _id
в Cursor
, и, предположительно, у вас его не будет. Вам нужно будет создать свой собственный адаптер, возможно, расширяя BaseAdapter
, который обрабатывает его.
Я думаю, что в качестве первичного ключа будут проблемы с производительностью, используя строки (UUID имеет 36 символов).
Возможно, но я буду несколько удивлен, если он превратится в материальную проблему с базами данных размером с устройство.
Однако я не вижу никакой другой возможности для реализации такой совместной системы синхронизации, поэтому я должен использовать UUID, правильно?
Вам нужен какой-то UUID для вашего сетевого протокола. Предположительно, вам понадобится этот UUID в вашей базе данных. Должен ли этот UUID быть основным ключом таблицы, я не могу сказать, потому что я не знаю вашу схему.
Другой возможностью было бы использовать первичный ключ с автоматическим добавлением целых чисел и использовать второй uuid столбца. Поэтому для работы с локальным устройством пользователей я бы использовал этот первичный ключ (integer) для JOINS и т.д., В то время как я использовал бы столбец uuid для синхронизации с другими пользователями.
Правильно. У вас будет таблица отображения UUID- > local integer ID, используйте UUID в сетевом протоколе и держите локальную базу данных в основном с использованием идентификаторов локального целого. Является ли это значительным улучшением производительности (особенно учитывая повышенную сложность схемы базы данных), я не могу сказать.
Что вы, ребята, думаете об этом подходе или, по вашему мнению, много работаете, так как вы не ожидаете значительную проблему с производительностью, используя UUID напрямую в качестве первичного ключа?
IMHO, либо выполните некоторые тесты производительности, чтобы получить некоторые конкретные сопоставимые данные, либо беспокоиться об этом, только если ваш ввод/вывод базы данных выглядит вялым.
Ответ 2
Один набор результатов производительности для UUID как двоичный и текст можно найти в несколько связанном с UUID/SQLite вопросе: fooobar.com/info/147691/...
В результате, как двоичные, так и строковые UUID могут быть эффективными в SQLite для Create и Query при индексировании. Отдельным компромиссом является то, является ли удобочитаемая строка предпочтительной для меньшего размера данных двоичного размера файла.