Автор работы: Пользователь скрыл имя, 05 Ноября 2009 в 13:11, Не определен
Лекции
2*) Решение проблемы зависимости от неподтвержденных обновлений с помощью механизма блокировки
Время | ТА | Значения | ТВ | Комментарий |
t0 | R=50 | start | ||
t1 | R=20 | UPDATE R=20 | М-запрос на R от ТВ и захват | |
t2 | start | |||
t3 | Сч1=SELECT R | С-запрос на R от ТА и отказ | ||
t4 | ждать | ТА ждет завершения ТВ (блокир) | ||
t5 | ждать | R=50 | ROLLBACK | ТВ заканчивается откатом, ТА разблокируется |
t6 | Сч1=SELECT R | Сч1 (ТА)=50, R=50 | С-запрос на R от ТА и захват |
3*)
Решение проблемы
Время | ТА | Значения | ТВ | Комментарий |
t0 | start | R1=40, R2=50, R3=30 | ||
t1 | Сч1=SELECT R1 | Сч1 (ТА)=40,
Сум (ТА)=40 |
С-запрос на R1 от TA и захват | |
t2 | Сч2=SELECT R2 | Сч2 (ТА)=50,
Сум (ТА)=90 |
С-запрос на R2 от TA и захват | |
t3 | start | |||
t4 | Сч3 (ТВ)=30 | Сч3=SELECT R3 | С-запрос на R3 от TВ и захват | |
t5 | R3=20 | UPDATE R3=Сч3-10 | М-запрос на R3 от TB и захват | |
t6 | Сч1 (ТВ)=40 | Сч1=SELECT R1 | С-запрос на R1 от ТВ и захват | |
t7 | UPDATE R1=Сч1+10 | М-запрос на R1 от ТВ и отказ, т.к. есть С-запрос на R1 от ТА | ||
t8 | ждать | ТВ ждет завершения ТА | ||
t9 | Сч3=SELECT R3 | ждать | С-запрос на R3 от ТА и отказ, т.к. есть М-запрос на R3 от ТВ | |
t10 | ждать | ждать | ТА ждет завершения ТВ | |
Тупик, который приведет к принудительному откату одной из транзакций |
Главная
идея этого подхода не в том, чтобы
изолировать объект в БД от другой
транзакции, а в том, чтобы создать
отдельную копию объекта для
каждой параллельной транзакции. Тогда
транзакции от своего начала и до конца
будут работать с собственными копиями
объекта. По завершении транзакции все
сделанные ей изменения могут быть перенесены
из ее копии объекта в БД.
Некоторые
обстоятельства:
1)
Очевидно, что беспрепятственно
изменить свою копию сможет
лишь одна из параллельных
транзакций, которая сделает это первой
(TA). СУБД не позволит другой транзакции
(TB) изменить тот же объект и, либо аварийно
завершит TB, либо переведет TB в ожидание
до конца TA, что зависит от заданных для
TB условий старта.
Если TB будет ждать завершения TA, то возможны два исхода:
а) TA подтверждает свои изменения (COMMIT), тогда TB аварийно завершается;
б)
TA отменяет свои изменения (ROLLBACK), тогда
TB переносит свои изменения в
БД и продолжает работать.
2)
Каждая параллельная
Решение
трех проблем с
помощью многоверсионных
объектов в СУБД Interbase
Объектом
для транзакции является строка.
Interbase
создает новую версию строки
всякий раз, когда какая-либо
транзакция изменяет или
По
запросу любой транзакции на чтение
этой строки, Interbase предоставляет ей
самую свежую версию строки, но уже
подтвержденную до старта этой транзакции.
1**)
Решение первой проблемы (утраченное
обновление)
Время | ТА | Значения | ТВ | Комментарий |
t0 | R (t0, TX)=50 | Последняя подтвержденная версия R на t0 | ||
t1 | start | |||
t2 | Сч1=SELECT R | Сч1 (ТА)=50 | ТА получает подтвержденную версию от времени t0<t1 | |
t3 | start | |||
t4 | Сч1 (ТВ)=50 | Сч1=SELECT R | ТВ получает подтвержденную версию от времени t0<t3 | |
t5 | UPDATE R=Сч1+15 | R (t5, ТА) = 65 ? | Не известно, будет ли подтверждено изменение | |
t6 | Сч1 (ТВ)=50 | Сч1=SELECT R | Версия от t5 для TB не доступна, так как t5>t3 | |
t7 | UPDATE R=Сч1-10 | TB блокируется, т.к. есть версия R от t5 и t5>t3 | ||
t8 | ждать | ТВ ждет завершения ТА | ||
t9 | COMMIT | R (t9,TA)=65 | конфликт | Подтвержденная версия от t9 для TB не доступна, т.к. t9>t3 |
t10 | ROLLBACK | TB должна отменить свои изменения | ||
t11 | start (ТВ') | |||
t12 | Сч1 (ТВ')=65 | Сч1=SELECT R | t12>t9 | |
t13 | R (t13, TB')=55 ? | UPDATE R=Сч1-10 | ||
t14 | R (t14, TB')=55 | COMMIT |
TA
беспрепятственно изменило R, поскольку
сделало это первой. TB не удалось
изменить R, так как она не "видела"
самой последней
(1**)
решает проблему (1) и, в отличие
от (1*), исключает тупиковую ситуацию.
2**)
Решение проблемы зависимости от неподтвержденных
обновлений с помощью многоверсионных
объектов
Время | ТА | Значения | ТВ | Комментарий |
t0 | R=50 | start | Последняя подтвержденная версия R на t0 | |
t1 | R(t1,TB)=20 ? | UPDATE R=20 | Не известно, будет ли подтверждено изменение | |
t2 | start | |||
t3 | Сч1=SELECT R | R(t3,TA)=50, Сч1(ТА)=50 | Последняя подтвержденная версия R на t3 | |
t4 | R=50, R(t4,TA)=50, Сч1(ТА)=50 | ROLLBACK | ТВ отменяет свои изменения и заканчивается, т.е. изменения ТВ в БД не переносятся | |
t5 | ТА может спокойно продолать работу |
3**)
Решение проблемы
Время | ТА | Значения | ТВ | Комментарий |
t0 | start | R1=40, R2=50, R3=30 | Последние подтвержденные версии R1, R2, R3 | |
t1 | Сч1=SELECT R1 | R1(t1,TA)=40, Сч1(ТА)=40, Сум(ТА)=40 | ||
t2 | Сч2=SELECT R2 | R1(t2,TA)=50, Сч2(ТА)=50, Сум(ТА)=90 | ||
t3 | R1(TB)=40, R2(TB)=50,
R3(TB)=30 |
start | ||
t4 | Сч3(ТВ)=30 | Сч3=SELECT R3 | ||
t5 | R3(TB)=20 ? | UPDATE R3=Сч3-10 | Не известно, будет ли подтверждено изменение | |
t6 | Сч1(ТВ)=40 | Сч1=SELECT R1 | ||
t7 | R1(TB)=50 ? | UPDATE R1=Сч1+10 | Не известно, будет ли подтверждено изменение | |
t8 | R1(TB)=50, R3(TB)=20
R1=50, R2=50, R3=20 |
COMMIT | Конфликт: подтвержденные версии R1 и R3 для ТА не доступны, т.к. t8>t0 | |
t9 | ROLLBACK | ТА должна сделать откат | ||
t10 | start (TA') | R1(TA')=50, R2(TA')=50,
R3(TA')=20 |
Последние подтвержденные версии R1, R2, R3 | |
t11 | Сч1=SELECT R1 | Сч1(ТА')=50, Сум(ТА')=50 | ||
t12 | Сч2=SELECT R2 | Сч2(ТА')=50, Сум(ТА')=100 | 50+50=100 | |
t13 | Сч3=SELECT R3 | Сч3(ТА')=20, Сум(ТА')=120 | 100+20=120
Получили правильный результат для ТА: 120 |
Существует две модели построения программ:
Процессно-ориентированная. В данной модели программа представляется как ряд последовательно выполняемых операций (процедур). Языки программирования, в которых реализован процессно-ориентированный подход к построению программ, называются процедурными.
Объектно-ориентированная. При использовании данной модели программа рассматривается как совокупность объектов – отдельных фрагментов кода, обеспечивающих выполнение определенных действий и объединяющих данные и методы управления ими.
Программа,
написанная на языке Object Pascal, состоит
из ряда разделов. Начало каждого раздела
указывается с помощью специальных зарезервированных
слов. В общем виде программа Object Pascal имеет
следующий вид:
Program Name_of_program Uses Unit1, Unit2,
Unit3 Label Label1, Label2 Type id_type1 = type_def1; id_type2 = type_def2; Var id_var1: type_def1; id_var2, id_var3:
id_type2; Const id_const1 = value1; id_const2 = value2; id_const3 = expression1; Procedure proc1; текст процедуры Function Func1: type_def1; текст функции begin текст программы end. |
Заголовок программы Раздел
объявления используемых модулей Раздел
объявления используемых меток Раздел
описания типов, определяемых пользователем Раздел
объявления переменных Раздел
описания констант Раздел
объявления процедур и функций, используемых
в программе |
Заголовок программы. В заголовке после служебного слова Program указывается имя программы.
Раздел объявления модулей. Начало данного раздела указывается с помощью директивы Uses.
Разделов объявления меток, типов, констант и переменных может быть несколько, и они могут следовать в любом порядке.
Раздел объявления меток. Начало раздела указывается с помощью директивы Label.
Раздел описания типов. В Object Pascal существует довольно большое количество стандартных типов. Однако при разработке программ, особенно при использовании объектно-ориентированного программирования, программисту необходима возможность создавать свои типы данных. Для описания пользовательских типов используется раздел объявления типов, начало которого определяет директивы Type. Самым простым вариантом объявления собственного типа является просто объявление типа, аналогично уже существующему, например:
Type
id_type1 = integer;
Раздел переменных. Начало раздела объявляется с помощью служебного слова Var. В данном разделе должны быть описаны все переменные, которые будут использоваться в программе.
Компилятор Object Pascal не допускает использование переменных, не объявленных в разделе Var. Объявление переменной, не используемой в программе, не приводит к ошибке компиляции, однако компилятор будет выдавать предупреждение о том, что переменная объявлена, но никогда не используется.
При
объявлении переменной указывается
идентификатор и через
var
id_var1: integer;
Идентификаторы переменных одного типа можно перечислять через запятую:
var
id_var1, id_var2, id_var3: integer;
Для нестандартных типов имя типа должно быть описано в разделе Type, находящемся выше раздела Var, в котором оно используется.
Раздел констант. Данный раздел содержит объявления констант и начинается с директивы Const. Константа фактически является переменной, значение которой устанавливается не в процессе выполнения программы, а на этапе компиляции. Значение константы не может изменяться программно. В объявлении константы можно использовать не только конкретные значения, но и выражения. Тип константы определяется присваиваемым ей значением или типом результата, получаемого при вычислении выражения.