0% found this document useful (0 votes)
21 views

BD2 Text and Sol Draft

This document summarizes a database lecture that covered: 1. Active databases and designing triggers to implement booking and cancellation policies for a bus ticketing system. 2. Classifying a concurrency control schedule according to several protocols. 3. Extracting information from an XML document using XQuery, including the projects involving the most people and a list of projects sorted by cost-effectiveness. 4. Estimating the cost of queries on tables stored in primary storage with and without secondary indexes.

Uploaded by

SaladSlayer
Copyright
© © All Rights Reserved
We take content rights seriously. If you suspect this is your content, claim it here.
Available Formats
Download as PDF, TXT or read online on Scribd
0% found this document useful (0 votes)
21 views

BD2 Text and Sol Draft

This document summarizes a database lecture that covered: 1. Active databases and designing triggers to implement booking and cancellation policies for a bus ticketing system. 2. Classifying a concurrency control schedule according to several protocols. 3. Extracting information from an XML document using XQuery, including the projects involving the most people and a list of projects sorted by cost-effectiveness. 4. Estimating the cost of queries on tables stored in primary storage with and without secondary indexes.

Uploaded by

SaladSlayer
Copyright
© © All Rights Reserved
We take content rights seriously. If you suspect this is your content, claim it here.
Available Formats
Download as PDF, TXT or read online on Scribd
You are on page 1/ 4

DATA BASES 2 – JANUARY 17TH, 2019 – DURATION: 2H 15M

PROF. SARA COMAI, PROF. DANIELE M. BRAGA


A. Active Databases (10 p.)
ROUTE (ROUTEID, FROM, TO, TIME, TOTALNUMBEROFSEATS, COST)
REQUEST (USEREMAIL, ROUTEID, DATE, NUMBEROFSEATS, USECANCELLATIONBONUS, ACCEPTED)
BOOKING (USEREMAIL, ROUTEID, DATE, NUMBEROFSEATS, USECANCELLATIONBONUS, TOTALCOST)
CANCELLATIONBONUS (USEREMAIL, STARTINGDATE, BONUSVALUE)
The schema above describes the ticketing system of a low-cost bus company. Design a set of triggers to implement the
following behavior. Whenever a new request arrives, availability of seats for the requested trip is checked: if seats are
sufficient, it is accepted, and the Accepted attribute (initially always equal to null) is set to true; otherwise, Accepted is set
to false. If the request is accepted, then it is added to BOOKING, and the total cost is calculated, possibly using bonuses.
If a booking is deleted, a cancellation bonus is emitted, for a value equal to 90% of the TotalCost and valid for one year
from the current date [management of the bonus expiration can be omitted for brevity]. If a user gets more than one bonus in the
same day, their values are summed up. The bonus can be used for other trips, if this is specified in the request. In such a
case, the value of the bonus is deducted from the total cost and the bonus value is consequently updated. If the user has
more than one bonus, the oldest one is used first, and if the bonus is smaller than the amount to be payed, other bonuses of
that user can be used, until the total cost is reached or the bonuses end. If a bonus is completely used, it is deleted.

B Concurrency Control (5 p.)


Classify this schedule w.r.t. VSR, CSR, 2PL, 2PL-strict, TS-mono, TS-multi, giving terse but precise justifications:
r1(A) r2(B) r3(A) r1(B) w3(C) w2(B) r2(C) w1(A) r3(C) w2(C)

C. XML (9 p.)
<!ELEMENT Company ( Person+, Project+ )>
<!ELEMENT Person ( Name, Role, … )>
<!ATTLIST Person id ID #REQUIRED>
<!ELEMENT Project ( Name, StartDate, Activity+ )>
<!ELEMENT Activity ( Code, Task+, Activity* )>
<!ELEMENT Task ( InitiallyPlannedBudget, CompletionPercentage, CostSoFar )>
<!ATTLIST Task PersonInCharge IDREF #REQUIRED>
The DTD above describes the ongoing projects carried out by a company. Each project brakes down into activities, and each
activities into elementary tasks, and possibly other sub-activities. Each task is assigned to a specific person, in charge of reporting
the current progress status (of course a task may be completed spending less than the initially planned budget, or be more costly
than planned, even at an early stage). Unspecified elements only contain PCData. Extract in XQuery:
(3 p.) 1. The Name of the project(s) that involve(s) the largest number of people.
(6 p.) 2. A list of the projects sorted by cost-effectiveness, defined as the ratio between the planned overall cost and the
actual expected overall cost at full completion. Assume that each task will either cost (i) as much as planned, if
not start yet (i.e., if completed at 0%), or (ii) proportionally to the cost already incurred for the completed fraction.

D. Physical Databases (6 p.)


A table TICKET(TkId, From, To, PassId, Date, DepTime, ArrTime) stores 390K tuples in 40K blocks in an entry-sequenced
primary store. A table PASSENGER(PassId, Name, Email, Birthdate) stores 30K tuples in a primary B+ tree built on PassId
with 3 levels and 2K leaf nodes. We know that val(To)=130 and val(Birthdate)=5K. Consider the following queries:
(1) select PassId as WentToRomeOnBitrhday (2) select PassId, count(*) from TICKET
from TICKET natural join PASSENGER where PassId in ( select PassId
where To = ‘Rome’ and from PASSENGER
day(Date) = day(Birthdate) and where Birthdate = ‘1/4/2000’ )
month(Date) = month(Birthdate) group by PassId
Describe briefly (but precisely) a reasonably efficient query plan and estimate its execution cost in the following scenarios
(cost estimations provided without a clear description of the associated plan will not be considered).
a) There are no secondary access structures;
b) Both tables have secondary hash indexes, TICKET built on PassId (3K blocks), PASSENGER on Birthdate (600 blocks).
A
CREATE TRIGGER AcceptRequest
AFTER INSERT ON REQUEST
FOR EACH ROW
WHEN (SELECT SUM(NumberOfSeats)
FROM BOOKING
WHERE RouteID=new.RouteID and Date=new.Date) + new.NumberOfSeats <
(SELECT TotalNumberOfSeats
FROM ROUTE
WHERE RouteID=new.RouteID)
BEGIN
UPDATE REQUEST
SET Accepted =”Yes”
WHERE UserEmail=new.UserEmail AND RouteID=new.RouteID AND Date=new.Date;
END;

A second trigger is then defined, with a negated condition to set Accepted=”No”.


In alternative, the condition is moved to an IF clause in the action part to consider the cases Accepted=“YES” and
Accepted=”No”.

CREATE TRIGGER BookAndComputeCost


AFTER UPDATE OF Accepted ON REQUEST
WHEN new.Accepted=”YES”
FOR EACH ROW
BEGIN
INSERT INTO BOOKING (new.UserEmail, new.RouteID, new.Date, new.NumberOfSeats,
new.UseCancellationBonus, new.NumberOfSeats*(SELECT Cost FROM ROUTE WHERE
RouteID=new.RouteID))
END;

CREATE TRIGGER InsertBonus


AFTER DELETE ON BOOKING
FOR EACH ROW
WHEN NOT EXISTS (SELECT *
FROM CANCELLATIONBONUS
WHERE UserEmail=old.UserEmail AND StartingDate=sysdate())
BEGIN
INSERT INTO CANCELLATIONBONUS VALUES (old.UserEmail, sysdate(), old.TotalCost*0.9)
END;

CREATE TRIGGER InsertBonus


AFTER DELETE ON BOOKING
FOR EACH ROW
WHEN EXISTS (SELECT * FROM CANCELLATIONBONUS
WHERE UserEmail=old.UserEmail AND StartingDate=sysdate())
BEGIN
UPDATE CANCELLATIONBONUS
SET BonusValue = BonusValue + old.TotalCost
WHERE UserEmail=old.UserEmail and StartingDate=sysdate();
END;

CREATE TRIGGER UseBonus


AFTER INSERT ON BOOKING | UPDATE OF TotalCost on BOOKING
FOR EACH ROW
WHEN new.UseCancellationBonus = “Y” AND TotalCost > 0
BEGIN
DECLARE Bonus number;
SELECT BonusValue INTO BONUS
FROM CANCELLATIONBONUS
WHERE UserEmail=new.UserEmail AND StartingDate = SELECT MIN (StartingDate)
FROM CANCELLATIONBONUS
WHERE UserEmail=new.UserEmail);
IF Bonus >= new.TotalCost
UPDATE BOOKING SET TotalCost = 0 WHERE UserEmail=new.UserEmail;
UPDATE CANCELLATIONBONUS
SET BonusValue=BonusValue-Bonus
WHERE UserEmail=new.UserEmail;
ELSE
UPDATE BOOKING SET TotalCost = TotalCost - Bonus WHERE UserEmail=new.UserEmail;
DELETE CANCELLATIONBONUS WHERE UserEmail=new.UserEmail;
END;

The schedule is clearly not in TS (r3 w1 on A and r3 w2 on C ).


It is in CSR and VSR (acyclic graph : T3T1T2).
A: r1 r3 w1
B: r2 r1 w2
C: w3 r2 r3 w2
It is outside 2PL strict (T3 releases A and C before commit) but inside 2PL:

Note that there are three lock upgrades and a lock downgrade (dashed).

C.1
let $maxcount := max( for $pj in doc(..)//Project
return count( distinct-values($pj//Task@PersonInCharge) ) )
for $p in doc(..)//Project
where count( distinct-values( $p//Task@PersonInCharge ) ) = $maxcount
return $p/Name

C.2
for $Proj in doc(..)//Project
let $Planned := sum( $Proj//Task/InitiallyPlannedBudget )
let $NotStarted := sum( $Proj//Task[CompletionPercentage=0]/InitiallyPlannedBudget )
let $Started := sum( for $t in $Proj//Task[ CompletionPercentage > 0 ]
return $t/CostSofar div $t/CompletionPercentage )
let $CostRatio := ( $NotStarted + $Started ) div $Planned
order by $CostRatio
return <Project>
{ $Proj/Name }
<PlannedCost> { $Planned } </PlannedCost>
<ExpectedCost> { $NotStarted + $Started } </ExpectedCost>
<Efficiency> { (1 - $CostRatio) * 100 , "%" } </Efficiency>
</Project>
D
Scenario (a)
1. Scan Ticket, lookup the PassId onto the B+ for the selected tickets to Rome, and check the date in main memory:
40K + 390K / val(To) ∙ ( 3 ) = 40K + 3K ∙ 3 = 49 K
2_dumb. Scan Passenger, scan the tickets for the selected Passengers born on 1/4/200, and count the tuples while scanning:
2K + 30K / val(To) ∙ ( 40K ) = 2K + 6 ∙ 40K = 242 K
2_smart. Scan Passenger, cache the PassIds of the FEW (6!) Passengers born on 1/4/200, and scan Tickets only once:
2K + 40K = 42 K
Scenario (b)
1. Both indexes are useless here, the cost is the same.
2. Find the 6 Passengers with the hash, then use the other hash to count their tickets (without retrieving the tuples!):
1 + 6 ∙ ( 1 + 1 ) = 13

You might also like