Скопируйте данные из таблицы и загрузите их в другую таблицу

У меня есть таблица "А" с 40 столбцами. Мне нужно скопировать данные из 20 определенных столбцов из «A» в другую таблицу «B», имеющую эти 20 столбцов. Будет около 3-10 миллионов записей. Что будет наиболее эффективным способом сделать это в PLSQL.


person cool_mo    schedule 09.07.2013    source источник
comment
Почему PL/SQL, почему не прямой SQL insert into ... select ...?   -  person Alex Poole    schedule 09.07.2013
comment
Ваш выбор тегов предполагает, что у вас уже есть ответ. Что вы ожидаете от нас?   -  person APC    schedule 09.07.2013
comment
Да, я реализовал это с помощью BULK COLLECT и FORALL. Я хотел бы знать, есть ли способ настроить это, чтобы повысить эффективность.   -  person cool_mo    schedule 09.07.2013
comment
@cool_mo Да, ты можешь стать лучше. Используйте оператор SQL. Если вам нужно, запустите его из блока PL/SQL, он будет работать нормально.   -  person the_slk    schedule 09.07.2013
comment
@the_slk Итак, INSERT INTO SELECT A.c1 , A.c2 из A (в блоке PLSQL), будет ли это более эффективным, чем использование BULK COLLECT в блоке PLSQL?   -  person cool_mo    schedule 09.07.2013
comment
Если вы ежедневно выполняете усечение и повторное заполнение и если не изменяете данные в таблице B, вы также можете рассмотреть материализованное представление, чтобы упростить повторную загрузку.   -  person Alex Poole    schedule 09.07.2013
comment
Мне просто любопытно - какое бизнес-обоснование для этого?   -  person Bob Jarvis - Reinstate Monica    schedule 10.07.2013


Ответы (2)


"Ежедневная таблица B будет усечена, и в нее будут вставлены новые данные из A."

Итак, самый эффективный способ сделать это — не делать этого. Вместо этого используйте материализованное представление; журнал материализованного представления в таблице A позволит вам фиксировать добавочные изменения и применять их ежедневно или в любом другом удобном для вас окне. Подробнее.

По сравнению с этим подходом использование ручного PL/SQL или даже чистого SQL смехотворно неэффективно.

person APC    schedule 11.07.2013

Нужно ли вам выполнять какое-либо преобразование данных или вы просто копируете данные прямо из одной таблицы в другую?

Самый простой способ сделать это, хотя вам придется создавать индексы отдельно.

create table B as (select A.c1, A.c2, A.c3..... from A);

Если таблица x уже существует, вы можете просто сделать

insert into B select A.c1, A.c2.... from A

Чтобы ускорить это, вы могли бы удалить все индексы в таблице x до тех пор, пока не будет выполнена вставка.

person Brian Hoover    schedule 09.07.2013
comment
Нет, сортировка данных не выполняется, просто нужно скопировать данные в Б. Ежедневная таблица «Б» будет усечена, и будут добавлены новые данные. Так что будет наиболее эффективным способом 1) Вставить в B, выбрать ИЛИ 2) ОПТОВЫЙ СОБИРАТЬ - person cool_mo; 09.07.2013
comment
Я никогда не проводил тест производительности. Это разовая работа? - person Brian Hoover; 09.07.2013
comment
я пробовал с INSERT INTO , но что мне делать, если мне нужно делать фиксацию после каждой вставленной строки 50000? - person cool_mo; 09.07.2013
comment
Нет. Ежедневная таблица Б будет усечена и в нее будут вставлены новые данные из А. - person cool_mo; 09.07.2013
comment
Тогда вам, вероятно, следует провести пробный запуск. Не должно занимать слишком много времени. - person Brian Hoover; 09.07.2013
comment
Да, проверю, но мне нужно делать коммит после каждых 50000. Возможно ли это? - person cool_mo; 09.07.2013
comment
Насколько я знаю, вам придется вручную отделять записи во вставке для выбора, поэтому, если это требование, вам, вероятно, будет лучше с хранимой процедурой. Если вы делаете это ежедневно, вы можете использовать триггер для каждой вставки/обновления, чтобы просто делать это после каждой новой записи. - person Brian Hoover; 09.07.2013
comment
@cool_mo - почему вы (думаете, что вам) нужно коммитить каждые 50000 строк? - person Alex Poole; 10.07.2013
comment
@ Alex Poole На самом деле это бизнес-требование - person cool_mo; 23.07.2013