schema.sqclass="underline"
□ CREATE TABLE p r o d u c t_ c h a n g e s (
p r o d u c t _ id INTEGER
CONSTRAINT p ro d _ ch a n g e s_ p k PRIMARY KEY,
p r o d u c t _ t y p e _ id INTEGER
CONSTRAINT p ro d _ c h a n g e s _ f k _ p r o d u c t _ t y p e s
REFERENCE p r o d u c t _ t y p e s ( p r o d u c t _ t y p e _ id ) ,
name VARCHAR2(30) NOT NULL,
d e s c r i p t i o n VARCHAR2(50) ,
p r i c e NUMBER(5, 2)
);
Следующий запрос показывает столбцы p r o d u c t _ id , p r o d u c t _ t y p e _ id ,
name и p r i c e для строк таблицы p ro d u c t_ c h a n g e s :
□ SELECT product_id, product_type_id, name, price
FROM product_changes;
PRODUCT ID PRODUCT TYPE ID NAME PRICE
1 1 Modern S c ie n c e 40
2 1 New C h em i s t r y 35
3 S u p e rn o v a 2 5 .9 9 13
2 Lu n a r L a n d in g 1 5 .9 9 14
2 S u bma r ine 1 5 .9 9 15
2 A i r p l a n e s 1 5 .9 9
Допустим, вы хотите слить строки из таблицы p ro d u c t_ c h a n g e s в таблицу
p r o d u c t s следующим образом.
Изменение содержимого таблиц 271
■ Для существующих строк с совпадающими значениями p ro d u c t _ t y p e _
i d в таблицах p r o d u c t s и p r o d u c t_ c h a n g e s следует обновить строки
таблицы products значениями столбцов, перечисленными в таблице
p ro d u c t_ c h a n g e s . Например, у товара № 1 в таблице p ro d u c t_ c h a n g e s
указана другая цена, чем в таблице products, так что цену для товара
№ 1 в таблице p r o d u c t s следует обновить. Аналогично, у товара № 2
в таблице p ro d u c t_ c h a n g e s изменены название товара и его цена, так
что таблица products должна быть обновлена. Наконец, у товара № 3
изменилось значение столбца p r o d u c t _ t y p e _ id , так что таблица
products должна быть обновлена.
■ Для новых строк в таблице p r o d u c t_ c h a n g e s необходимо вставить эти
строки в таблицу p r o d u c t s . Товары № 13, №14 и № 15 являются новыми
по отношению к таблице products, поэтому должны быть вставлены
в таблицу products.
Следующий пример осуществляет слияние именно так, как оно было
определено выше, чтобы влить изменения из p ro d u c t_ c h a n g e s в p r o d u c t s :
□ MERGE INTO p r o d u c t s p
USING p ro d u c t_ c h a n g e s pc ON (
p . p r o d u c t _ id = p c . p r o d u c t _ id
)
WHEN MATCHED THEN
UPDATE
SET
p . p r o d u c t _ t y p e _ id = p c . p r o d u c t _ t y p e _ id ,
p.name = pc.name,
p . d e s c r i p t i o n = p c . d e s c r i p t i o n ,
p . p r i c e = p c . p r i c e
WHEN NOT MATCHED THEN
INSERT (
p . p r o d u c t _ id , p . p r o d u c t _ t y p e _ id , p.name,
p . d e s c r i p t i o n , p . p r i c e
) VALUES (
p c . p r o d u c t _ id , p c . p r o d u c t _ t y p e _ id , pc.name,
p c . d e s c r i p t i o n , p c . p r i c e
);
6 rows merged.
Примечание В папке SQL вы найдёте сценарий по имени merge_example.sql, который содержит
предыдущее выражение MERGE.
Следует отметить ряд связанных с оператором MERGE моментов.
■ Фраза MERGE INTO указывает название таблицы, в которую будут вливаться
строки. В примере таблицей, в которую будут вливаться строки,
является таблица products, имеющая псевдоним р, который используется
при ссылках в остальной части оператора MERGE.
272 Гпава 8
■ Фраза USING ... ON определяет соединение таблиц. В нашем примере
соединение производится по столбцу p r o d u c t _ id из таблиц products
и p r o d u c t_ c h a n g e s . Таблица p ro d u c t_ c h a n g e s имеет псевдоним рс, который
используется при ссылках в остальной части оператора
MERGE.
■ Фраза WHEN MATCHED THEN задаёт действия, предпринимаемые, когда
для строки оказывается выполненной фраза USING ... ON. В примере
подобным действием будет оператор UPDATE, устанавливающий значения
столбцов p r o d u c t _ t y p e _ id , name, d e s c r i p t i o n и p r i c e существующей
строки таблицы products равными значениям соответствующих
столбцов таблицы p ro d u c t_ c h a n g e s .
■ Фраза WHEN NOT MATCHED THEN задаёт действия, предпринимаемые, когда
фраза USING .. . ON для строки оказывается невыполненной. В примере
подобным действием будет оператор INSERT, который добавляет
строку в таблицу p r o d u c t s , используя значения столбцов из строки
таблицы p ro d u c t_ c h a n g e s .
Если выполнить предыдущий оператор MERGE, вы увидите информацию
о том, что обработано шесть строк. Это будут строки со значениями
p r o d u c t _ id 1, 2, 3, 13, 14 и 15. Следующий запрос извлекает эти шесть слитых
строк из таблицы p r o d u c t s :
П SELECT product_id, product_type_id, name, price
FROM products
WHERE product_id IN (1, 2, 3, 13, 14, 15);
ID PRODUCT_TYPE_ID NAME PRICE
1 1 Modern S c ie n c e 40
2 1 New C h em i s t r y 35
3 1 S upe rno va 2 5 .9 9
13 2 L u n a r L an d in g 1 5 .9 9
14 2 Subma r ine 15 .9 9
15 2 A i r p l a n e s 15 .9 9
Были выполнены следующие изменения:
■ У товара № 1 появилась новая цена.
■ У товара № 2 появились новое название и цена.
■ У товара № 3 изменился идентификатор типа товара.
■ Товары 13, 14 и 15 являются новыми.
Транзакции базы данных
Транзакцией базы данных называется группа операторов SQL, которая
выполняет логическую единицу работы. Можно представлять себе транзакцию
как неразделимый набор операторов SQL, который должен быть