#sql #sql-server #oracle #sql-server-2005 #tsql
#sql #sql-сервер #Oracle #sql-server-2005 #tsql
Вопрос:
Я сохраняю различные действия с идентификаторами как 1,2,3,4 последовательно.
Если я удалю 2-ю запись (идентификатор 2), как я могу обновить, чтобы 3 стало 2, а 4 стало 3?
Заранее спасибо
Комментарии:
1. Зачем вам нужно это делать? Не должно иметь значения, есть ли пробелы. Оба Oracle и SQL Server поддерживают
ROW_NUMBER
, если вам нужно получить непрерывную последовательность чисел из идентификаторов.2. Вопрос не в том, как, а почему? Чего вы пытаетесь достичь, гарантируя сохранение последовательных чисел в таблице?
3. frds … Это сокращение от fjords ?
Ответ №1:
update table set col1 = col1-1 where col1>2
Комментарии:
1. Если OP использует фактический
identity
столбец в SQL Server, это не сработает, поскольку они не подлежат обновлению.2. @Martin — yups это правда, что вы не можете изменить
3. что такое OP? Здесь, пожалуйста, дайте мне знать
4. «OP» означает «оригинальный плакат» — в данном случае, вы.
Ответ №2:
Ответ 1. Вы не хотите. Вся цель поля id заключается в том, чтобы оно было неизменяемым.
Ответ 2. Вы не хотите. Если вам нужно это сделать, поле id — это вообще не поле id, а поле данных.
Ответ 3. Удалите записи и вставьте их снова с новыми номерами. Вы можете видеть, что это становится очень дорогостоящим, если количество строк велико.
Комментарии:
1. во многих случаях, если вы удаляете и повторно вставляете, удаленные идентификаторы не будут использоваться повторно, вместо этого будет использоваться новый неиспользуемый идентификатор в последовательности
Ответ №3:
Как насчет использования вместо этого подхода со связанным списком, где каждое действие указывает на следующее?
select * from activity;
---- ---------
| id | next_id |
---- ---------
| 1 | 2 |
| 2 | 3 |
| 3 | 4 |
| 4 | 5 |
| 5 | NULL |
---- ---------
Если вы хотите удалить действие с ID = 2, вам необходимо обновить строку, которая указывает на ID = 2, на строку, на которую ранее указывал ID = 2.
update activity
set next_id = 3
where id = 1;
delete
from activity
where id = 2;
---- ---------
| id | next_id |
---- ---------
| 1 | 3 |
| 3 | 4 |
| 4 | 5 |
| 5 | NULL |
---- ---------
Если у вас очень длинные списки и вы беспокоитесь о производительности DML, это может быть хорошим вариантом. Недостатком этого метода является то, что сложнее запрашивать таблицу.
Комментарии:
1. 1 Но не было бы лучше описать это как односвязный список ?
2. @oneday, да, я обновил ответ, чтобы использовать правильную терминологию.