Использование последовательности в существующей таблице - PullRequest
1 голос
/ 01 марта 2010

У меня есть таблица, которую люди вставляют в получение первичного ключа, выполняя

SELECT max(id)+1 from table_a;

Я хочу добавить некоторые записи в эту таблицу с помощью INSERT INTO table_a SELECT ... FROM table_b, table_c ... простого сценария SQL, и мне интересно, как генерировать первичные ключи. Моей первой мыслью было создание временной последовательности, но у Oracle, очевидно, нет select setval для установки первого значения. Так как же получить текущее значение max (id) +1, чтобы установить параметр «start with» для моей последовательности?

Я нашел в сети что-то, что, как мне показалось, будет работать:

COLUMN S new_value st select max(id)+1 S from  table_a;
CREATE SEQUENCE cra_seq start with &st;

Но на самом деле он не использует st в CREATE SEQUENCE, а вместо этого предлагает мне ввести его, а это не то, что мне нужно.

Ответы [ 4 ]

3 голосов
/ 01 марта 2010

Это что-то вроде того, что вы хотите?

  1  declare
  2    id  integer;
  3  begin
  4    select max(rownum)+1 into id from dual;
  5    execute immediate 'create sequence myseq start with '||TO_CHAR(id);
  6* end;
  7  /
1 голос
/ 01 марта 2010

Не могли бы вы использовать функцию row_number следующим образом:

Insert Destination( Id, ...)
Select row_number() over( order by TableA.Col1... ) + MaxDestination.MaxId + 1 Num
 , ....
From TableA, TableB,...
 Cross Join ( Select Max(Id) MaxId From Destination ) MaxDestination
0 голосов
/ 26 марта 2014

В PostgreSQL:

CREATE SEQUENCE new_seq;
ALTER TABLE existing_table ADD COLUMN new_serial_column bigint DEFAULT 0;
UPDATE existing_table SET new_serial_column = nextval('new_seq');
ALTER TABLE existing_table ALTER COLUMN new_serial_column SET NOT NULL;
ALTER TABLE existing_table ALTER COLUMN new_serial_column SET DEFAULT nextval('new_seq');

Хотя этот код не идемпотентен, поэтому проверьте, что вы еще не создали новую последовательность, что-то вроде:

CREATE FUNCTION fixup_existing_table() RETURNS void AS $$
DECLARE
    new_id bigint;
    seq_column_exists integer;
BEGIN
    SELECT Count(column_name) INTO seq_column_exists FROM information_schema.columns WHERE table_name='existing_table' and column_name='new_serial_column';
IF seq_column_exists != 0 THEN RETURN; END IF;

    CREATE SEQUENCE new_seq;
    ALTER TABLE existing_table ADD COLUMN new_serial_column bigint DEFAULT 0;
    UPDATE existing_table SET new_serial_column = nextval('new_seq');
    ALTER TABLE existing_table ALTER COLUMN new_serial_column SET NOT NULL;
    ALTER TABLE existing_table ALTER COLUMN new_serial_column SET DEFAULT nextval('new_seq');
END;
$$ LANGUAGE plpgsql;

Затем вы можете безопасно вызывать: SELECT fixup_existing_table (), чтобы изменять схему столько раз, сколько хотите, то есть вызывать какой-то тупой скрипт обновления.

0 голосов
/ 01 марта 2010

Вы можете использовать аналитическую функцию row_number для генерации номеров строк (от 1 до N).

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

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...