Обзор
Я дам четыре решения, начиная с самых простых. С каждым решением я объясню ситуации, в которых это применимо.
Каждое из этих решений предполагает, что базы данных А и В имеют следующие таблицы:
create table Terms
(
ID int identity(1,1),
Text nvarchar(MAX)
)
create table Relationships
(
ParentID int,
ChildID int
)
раствор 1
Это самое простое решение. Его следует использовать, если:
- Условия с одинаковым текстом, могут быть объединены вместе
Ниже будет объединить все условия и отношения из А в В:
insert into A.Terms (Text)
select Text
from A.Terms
where Text not in (select Text from B.Terms)
insert into B.Relationships (ParentID, ChildID)
select
(select ID
from B.Terms BTerms inner join A.Terms ATerms on BTerms.Text = ATerms.Text
where ATerms.ID = Relationships.ParentID),
(select ID
from B.Terms BTerms inner join A.Terms ATerms on BTerms.Text = ATerms.Text
where ATerms.ID = Relationships.ChildID)
from A.Relationships
В основном вы первый экземпляр термины, затем скопируйте отношения, сопоставляющие старый идентификатор с новым идентификатором на основе текста.
Примечание. В вашем вопросе вы указываете, что члены не пересекаются между двумя входными базами данных. В этом случае пункт where
в первом insert into
может быть опущен.
Решение 2
Это следующее простым решение. Его следует использовать, если:
- Условия с одинаковым текстом должны быть различны, и
- Вы можете добавить столбец в таблицу назначения
Первый добавить столбец INT таблицу Условия называется «OldID», а затем использовать следующее, чтобы объединить все условия и отношения от а до Б:
insert into A.Terms (Text, OldID)
select Text, ID
from A.Terms
where Text not in (select Text from B.Terms)
insert into B.Relationships (ParentID, ChildID)
select
(select ID from B.Terms where OldID = ParentID),
(select ID from B.Terms where OldID = ChildID)
from A.Relationships
Solution 3
Это решение использует итерацию.Его следует использовать, если:
- Условие с одинаковым текстом должно быть различно, и
- Вы не можете изменить таблицу назначения и
- Либо (а) вашего идентификатор столбца столбец идентификаторов (в Oracle, это означает, что он имеет триггер, который использует последовательность), или (б) вы хотите общий метод, который будет работать с любой технологией баз данных
Ниже будет объединить все термины и RELAT ionships из А в В:
declare TermsCursor sys_refcursor;
begin
-- Create temporary mapping table
create table #Temporary (OldID int, NewID int)
-- Add terms one at a time, remembering the id mapping
open TermsCursor for select * from A.Terms;
for term in TermsCursor
loop
insert into B.Terms (Text) values (term.Text) returning ID into NewID;
insert into Temporary (OldID, NewID) values (term.ID, NewID);
end loop;
-- Transfer the relationships
insert into B.Relationships (ParentID, ChildID)
select
(select ID
from B.Terms BTerms inner join Temporary on BTerms.ID = Temporary.NewID
where Temporary.OldID = Relationships.ParentID),
(select ID
from B.Terms BTerms inner join Temporary on BTerms.ID = Temporary.NewID
where Temporary.OldID = Relationships.ChildID),
from A.Relationships
-- Drop the temporary table
drop table #Temporary
end
Solution 4
Это решение Oracle конкретных, требует, чтобы знать последовательность, используемую для генерации значений ID, и является менее эффективным, чем некоторые из других решений , Его следует использовать, если:
- Условия с одинаковым текстом должны быть различны, и
- Вы не можете изменить таблицу назначения и
- Вы имеете доступ к последовательности, который генерирует свой идентификатор столбца, и
- Вы в порядке, используя techinique, что не будет порт на технологии баз данных не-Oracle
Ниже будет объединить все условия и отношения из а в в:
-- Create temporary mapping table
create table #Temporary (OldID int, NewID int)
-- Add terms to temporary mapping table
insert into #Tempoarary (OldID, NewID)
select ID, sequence.nexval
from A.Terms
-- Transfer the terms
insert into B.Terms (ID, Text)
select NewID, Text
from A.Terms inner join Temporary on ID = OldID
-- Transfer the relationships
insert into B.Relationships (ParentID, ChildID)
select
(select ID
from B.Terms BTerms inner join Temporary on BTerms.ID = Temporary.NewID
where Temporary.OldID = Relationships.ParentID),
(select ID
from B.Terms BTerms inner join Temporary on BTerms.ID = Temporary.NewID
where Temporary.OldID = Relationships.ChildID),
from A.Relationships
-- Drop the temporary table
drop table #Temporary
Не совсем ответ, но Вы рассмотрели с помощью PERL или питона скрипт для обработки шага? – Pace
Я боюсь, что SQL-древовидная структура действительно похожа на квадратную привязку к круглой дыре. Возможность использования только чрезмерного количества грубой силы. –
Не ответ на ваш вопрос, но есть ли какая-то конкретная причина, связанная с отношениями родителя/ребенка в отдельной таблице? Если каждый термин может иметь только один родитель, тогда таблица терминов может иметь родительский столбец. Когда вам нужно найти детей, вы можете использовать инструкцию «выбрать-из-за-соединитесь с». Это также сделало бы корневые узлы более очевидными, так как их родительский столбец был бы нулевым. – Aaron