Функция автоматического увеличения в базе данных

Я использую SQL Server, и когда я создаю новую таблицу, я делаю определенное поле автоматическим приращением основной ключ. Проблема в том, что некоторые люди сказали мне, что при создании поля для автоматического первичного ключа при удалении любой записи (они не заботятся о номере номера автоматического увеличения) поле увеличивается, поэтому в какой-то момент - если тип моего поля равен Например, целое число - диапазон целых чисел будет полностью поглощен, и у меня будут проблемы. Поэтому они говорят мне больше не использовать эту функцию.

Лучшее решение - сделать это через код, получив максимум моего первичного ключа, а затем, если значение не существует, max будет 1 другим мудрым max + 1.

Любые предложения по этой проблеме? Могу ли я использовать функцию автоматического увеличения?

Я хочу также знать случаи, которые не являются предпочтительными для использования автоматического приращения.. и альтернативы...

note: этот вопрос является общим, не относящимся к какой-либо СУБД, я хочу знать, это правда и для СУБД, таких как ORACLE, Mysql, INFORMIX,....

Большое спасибо.

Ответ 1

Вы должны использовать столбцы идентификации (автоинкремент). Тип данных bigint может хранить значения до 2 ^ 63-1 (9,223,372,036,854,775,807). Я не думаю, что ваша система скоро достигнет этого значения, даже если вы вставляете и удаляете множество записей.

Если вы реализуете метод, который вы предлагаете правильно, у вас будет много проблем с блокировкой. В противном случае вам придется иметь дело с исключениями, сброшенными из-за нарушения ограничений (или даже хуже - не уникальных значений, если нет ограничения первичного ключа).

Ответ 2

Тип данных int в SQL Server может содержать значения от -2,147,483,648 до 2,147,483,647.

Если вы засеваете свой столбец идентификационной информации с помощью 2,147,483,648, например. FooId identity(-2,147,483,648, 1), тогда у вас есть более 4 миллиардов значений для игры.

Если вы действительно думаете, что этого все еще недостаточно, вы можете использовать bigint, который может хранить значения от -9,223,372,036,854,775,808 до 9,223,372,036,854,775,807, но это почти гарантированно будет излишним. Даже при больших объемах данных и/или большом количестве транзакций вы, вероятно, либо исчерпаете дисковое пространство, либо исчерпаете срок службы вашего приложения, прежде чем исчерпываете значения идентификатора при использовании int и почти наверняка при использовании bigint.

Подводя итог, вы должны использовать столбец идентификатора, и вам не нужно заботиться о пробелах в значениях, так как: a) у вас есть достаточное количество кандидатов и b) это абстрактное число без логического значения.

Если вы хотите реализовать решение, которое вы предлагаете, с кодом следующего столбца идентификации, вам нужно будет рассмотреть concurrency, так как вам придется синхронизировать доступ к текущему максимальному значению идентификации между двумя конкурирующими транзакциями. В самом деле, вы можете в конечном итоге привести к значительному снижению производительности, поскольку вам нужно будет сначала прочитать максимальное значение, вычислить и затем вставить (не говоря уже о дополнительной работе, связанной с синхронизацией параллельных транзакций). Если, однако, вы используете столбец идентификатора, concurrency будет обработан для вас механизмом базы данных.

Ответ 3

Продолжайте использовать функцию идентификации с PK в SQL Server. В mysql есть также функция автоматического увеличения. Не беспокойтесь о том, что у вас заканчивается целочисленный диапазон, до этого не хватит места на жестком диске.

Ответ 4

Решение, которое они предлагают, может и, скорее всего, создаст проблему проблемы и/или масштабируемости concurrency. Если два сеанса используют метод Max, который вы описываете в одно и то же время, они могут иметь одинаковый номер, а затем оба пытаются добавить его одновременно. Это создаст нарушение ограничения.

Вы можете обойти эту проблему, заблокировав таблицу или поймав исключения, и продолжайте повторную вставку. Но это действительно плохой способ сделать что-то. Блокировка уменьшит производительность и вызовет проблемы с масштабируемостью (и если вы планируете столько записей, чтобы беспокоиться о переполнении int, вам понадобится масштабируемость).

Поля идентичности - это атомарные операции. Две сессии не могут создать одно и то же поле идентификации, поэтому эта проблема не существует при ее использовании.

Если вы обеспокоены тем, что поле идентификации может переполняться, используйте более широкий тип данных, например bigint. Вам будет сложно создать достаточное количество записей для переполнения.

Теперь существуют веские причины НЕ использовать поле идентификации, но это не один из них.

Ответ 5

Я бы посоветовал использовать параметр Identity/Auto-increment, потому что:

  • В SQL Server 2005/2008 реализована реализация. Подробнее

  • Это не работает, если вы собираетесь использовать ORM для сопоставления базы данных с объектами. Подробнее

Я бы посоветовал вам использовать генератор Hi/Lo, если вы обычно обращаетесь к своей базе данных через программу и не зависите от отправки инструкций вставки в БД. Вы можете прочитать об этом во второй ссылке.