Как узнать, уникален ли индекс SQLite?(С SQL)

StackOverflow https://stackoverflow.com/questions/157392

  •  03-07-2019
  •  | 
  •  

Вопрос

Я хочу узнать с помощью SQL-запроса, является ли индекс УНИКАЛЬНЫМ или нет.Я использую SQLite 3.

Я попробовал два подхода:

SELECT * FROM sqlite_master WHERE name = 'sqlite_autoindex_user_1'

Возвращает информацию об индексе («тип», «имя», «имя_таблицы», «корневая страница» и «sql»).Обратите внимание, что столбец sql пуст, когда индекс автоматически создается SQLite.

PRAGMA index_info(sqlite_autoindex_user_1);

Это вернет столбцы индекса («seqno», «cid» и «name»).

Есть еще предложения?

Редактировать: Приведенный выше пример относится к автоматически сгенерированному индексу, но мой вопрос касается индексов в целом.Например, я могу создать индекс с помощью «СОЗДАТЬ УНИКАЛЬНЫЙ ИНДЕКС index1 ПРИ посещении (пользователь, дата)».Кажется, ни одна команда SQL не покажет, является ли мой новый индекс УНИКАЛЬНЫМ или нет.

Это было полезно?

Решение

PRAGMA INDEX_LIST('table_name');

Возвращает таблицу с тремя столбцами:

  1. seq Уникальный числовой идентификатор индекса
  2. name Название индекса
  3. unique Флаг уникальности (ненулевой, если UNIQUE индекс.)

Затем просто просматривайте полученные строки, пока не увидите имя индекса, который вы хотите запросить (к сожалению, у вас нет WHERE пункт в PRAGMA заявление.)

Другие советы

Поскольку никто не дал хорошего ответа, я думаю, что лучшим решением будет следующее:

  • Если индекс начинается с «sqlite_autoindex», это автоматически сгенерированный индекс для одного УНИКАЛЬНОГО столбца.
  • В противном случае найдите ключевое слово UNIQUE в столбце sql таблицы sqlite_master примерно так:

    ВЫБЕРИТЕ * ИЗ sqlite_master ГДЕ type = 'index' И sql LIKE '%UNIQUE%'

вы можете программно создать оператор выбора, чтобы увидеть, указывают ли какие-либо кортежи на более чем одну строку.Если вы получите три столбца: foo, bar и baz, создайте следующий запрос

select count(*) from t
group by foo, bar, baz
having count(*) > 1

Если это возвращает какие-либо строки, ваш индекс не уникален, поскольку данному кортежу соответствует более одной строки.Если sqlite3 поддерживает производные таблицы (у меня пока нет необходимости, поэтому я не знаю навскидку), вы можете сделать это еще более кратким:

select count(*) from (
    select count(*) from t
    group by foo, bar, baz
    having count(*) > 1
)

Это вернет набор результатов из одной строки, обозначающий количество повторяющихся наборов кортежей.Если положительный, ваш индекс не уникален.

Вы близки:

1) Если индекс начинается с "sqlite_autoindex", это автоматически сгенерированный индекс для первичного ключа.Однако это будет в sqlite_master или sqlite_temp_master таблицы в зависимости от того, является ли индексируемая таблица временной.

2) Вам нужно следить за именами таблиц и столбцов, содержащими подстроку unique, поэтому вы хотите использовать:

SELECT * FROM sqlite_master WHERE type = 'index' AND sql LIKE 'CREATE UNIQUE INDEX%'

См. документацию веб-сайта sqlite на Создать индекс

Начиная с sqlite 3.16.0 вы также можете использовать прагматические функции:

SELECT distinct il.name
  FROM sqlite_master AS m,
       pragma_index_list(m.name) AS il,
       pragma_index_info(il.name) AS ii
 WHERE m.type='table' AND il.[unique] = 1;

В приведенном выше операторе будут перечислены все имена уникальных индексов.

SELECT DISTINCT m.name as table_name, ii.name as column_name
  FROM sqlite_master AS m,
       pragma_index_list(m.name) AS il,
       pragma_index_info(il.name) AS ii
 WHERE m.type='table' AND il.[unique] = 1;

Приведенный выше оператор вернет все таблицы и их столбцы, если столбец является частью уникального индекса.

Из документы:

Функции с табличным значением для функции PRAGMA были добавлены в SQLite версии 3.16.0 (2017-01-02).Предыдущие версии SQLite не могут использовать эту функцию.

Лицензировано под: CC-BY-SA с атрибуция
Не связан с StackOverflow
scroll top