Добавил:
Upload Опубликованный материал нарушает ваши авторские права? Сообщите нам.
Вуз: Предмет: Файл:
Lekcii_OBD.doc
Скачиваний:
1
Добавлен:
01.07.2025
Размер:
5 Мб
Скачать
☆

12.4. Управління транзакціями в мовах програмування.

Ніяка СУБД не має внутрішньої можливості встановити, які саме зміни повинні бути сприйняті як єдине ціле (як одна логічна одиниця).

Тому повинен існувати метод, що дозволяє вказувати границі кожної транзакції ззовні, з боку користувача. У більшості мов маніпулювання даними для вказівки границь окремих транзакцій використовуються оператори BEGIN TRANSACTION, COMMIT і ROLLBACK (або їхні еквіваленти).

Якщо ці обмежники не були використані, уся виконувана програма розцінюється як одна єдина транзакція. СУБД автоматично виконає команду COMMIT при нормальному завершенні цієї програми. Аналогічно, у випадку її аварійного завершення в базі даних автоматично буде виконана команда ROLLBACK.

Тому необхідно старатись, щоб пишучі транзакції були короткими.

Керування паралельністю. Проблеми паралелізму.

Найважливішою метою створення баз даних є організація паралельного доступу багатьох користувачів до спільно використовуваних даних. Забезпечити паралельний доступ нескладно, якщо всі користувачі будуть тільки читати дані, поміщені в базу. У цьому випадку робота кожного з них не робить ніякого впливу на роботу інших користувачів. Однак, якщо два або більше користувачі одночасно звертаються до бази даних і хоча б один з них має на меті обновити збережену в базі інформацію, можливий взаємний вплив процесів один на одного, здатний привести БД у суперечливий стан.

При цьому можливі наступні потенційні проблеми при виконанні транзакцій:

  • проблема загубленого відновлення,

  • проблему залежності від нефіксованих результатів

проблему неузгодженої обробки.

Проблема загубленого відновлення.

Результати успішно завершеної операції відновлення однієї транзакції можуть бути перекриті результатами виконання іншої транзакції. Ця аномалія відома як проблема загубленого відновлення.

Її суть ілюструється наступним прикладом:

Час

Транзакція Т1

Транзакція Т2,

Поле balx

t1

begin transaction

100

t2

read(bal(t2))

begin transaction

100

t3

balT1(t3) = bal(t2) + 100

Read(bal(t3))

100

t4

write (balT1(3))

bal(t4) = balT2(t3)- 10

200

t5

commit

Write (balT2(t4))

90

t6

commit

90

У цьому прикладі транзакція T1 виконується паралельно з транзакцією Т2. Транзакція Т1 виконує занесення 100грн. на рахунок bal, а Т2 знімає 10грн. з цього ж рахунку, на якому з початку знаходиться 100грн.

Якщо ці транзакції будуть виконуватися послідовно, без чергування їх операцій, то після завершення роботи на рахунку буде знаходитися сума в 190грн., - причому незалежно від порядку виконання транзакцій

Транзакція Т1 починаються в момент часу t1, а Т2 в момент часу t2. Кожна з них зчитує початкове значення суми на рахунку bal, рівне 100грн. Потім транзакція Т1 збільшує суму на 100грн. і записує результат, рівним 200грн., у базу даних — на рахунок bal(t4). Тим часом транзакція T2 зменшує значення своєї копії початкової суми на рахунку і записує отримане значення, рівним 90грн. у базу даних на рахунок bal(t5)., перекриваючи результат попереднього відновлення. У результаті з рахунку "зникає" 100грн.

Уникнути втрати результатів виконання транзакції Т1 можна, заборонивши транзакції t2 зчитувати вихідне значення на рахунку bal аж до завершення виконання транзакції Т1.

Проблема залежності від нефіксованих результатів.

Проблема залежності від нефіксованих результатів виникає в тому випадку, якщо одна з транзакцій одержить доступ до проміжних результатів виконання іншої транзакції до того, як вони будуть зафіксовані в базі даних.

Час

Транзакція Т3

Транзакція T4

Поле balх

t1

begin transaction

100

t2

read(balx)

100

tз

bal(t3) = bal(t2) + 100

100

t4

begin transaction

write (bal(t3))

200

t5

Read(bal(t5))

200

t6

bal(6) = bal(t5) -10

rollback

100

t7

Write (bal(t6))

190

t8

commit

190

У прикладі транзакція Т4 збільшує значення суми на рахунку bal до 200грн., після чого виконання транзакції скасовується, з відновленням початкового значення на рахунку bal, рівним 100грн.

Однак до цього моменту транзакція Т3 уже встигла зчитати змінене значення рахунка bal=200грн. і використала саме це значення при виконанні операції зняття грошей з рахунку, після чого зафіксувала в базі даних невірний результат 190грн. замість 90грн.

Причина виконання відкату транзакції Т4 несуттєва – наприклад при її виконанні була виявлена деяка помилка (введено невірний номер рахунку).

Джерелом помилки є припущення транзакцією Т3, що виконана в транзакції Т4 зміна буде успішно зафіксована в базі даних, хоча насправді мав місце відкат транзакції.

Проблему можна усунути, заборонивши транзакції Т3 зчитувати значення рахунку bal доти, поки транзакція Т4 не буде або зафіксована, або скасована.

Проблема неузгодженої обробки.

В обох приведених вище прикладах мова йшла про транзакції, що виконували відновлення даних у базі, наявність взаємного впливу між якими і викликало суперечливий стан БД.

Однак транзакції, що тільки зчитують інформацію з бази даних, також можуть давати невірні результати, якщо їм будуть доступні для читання проміжні результати паралельно виконуваних і ще не завершених транзакцій, що обновляють інформацію в базі. Цю проблему ще називають читанням сміття

Час

Транзакція Т5

Транзакція Т6

Поле bal1

Поле bal2

Поле bal3

Поле sum

t1

begin transaction

100

50

25

t2

begin transaction

sum = 0

100

50

25

0

t3

read(bal1(t3))

read (bal(t3))

100

50

25

0

t4

bal1(t4) = bal1(t3) – 10

sum = sum + bal(t3)

100

50

25

100

t5

write (bal1(t4))

read(bal2(t5))

90

50

25

100

t6

read(bal3(t6))

sum = sum + bal2(t5)

90

50

25

150

t7

Bal3(t7) = bal3(t6) + 10

90

50

25

150

t8

write (bal3(t7))

90

50

35

150

t9

commit

read (bal3(t9))

90

50

35

150

t10

sum = sum + bal3(t9)

90

50

35

185

t11

commit

90

50

35

185

Транзакція Т6 обчислює суму залишків на рахунках bal1= 100грн., bal2=50грн. і bal3= 25грн.

Паралельно з Т6 транзакція Т5 здійснює переказ 10грн. з рахунку bal1 на рахунок bа13.

В результаті значення суми, отримане транзакцією Т6 є невірним: 185грн. замість 175грн.

Ця проблема може бути усунута шляхом, заборони транзакції Т6 зчитувати значення на рахунках bal1 і bal3 доти, поки транзакція Т5 не зафіксує виконані нею відновлення.

Використання протоколу двох фазного блокування для усунення проблем.

Соседние файлы в предмете [НЕСОРТИРОВАННОЕ]