dtl
Category: utilities | Component type: type |
ValidatedObject's maintain state information that allows them to determine whether they are in a valid state or have been corrupted. Once an operation is performed in one of these self-validating classes that detects that the object is no longer in a valid state, the operation will throw a ValidityException. To get validation facilties for an object, simply derive from ValidatedObject. You can choose whether a method needs to validate the object or not by calling validate()at the beginning of the method if you wish to validate the object's state. To define the critieria used to define whether the object is in a valid state or not, override the valid() method. Often, in your valid() method, you may wish to test whether the object is already valid to save some work as no further testing is required if the object is found to already be invalid. Unless you override the revalidate() method, once an object becomes invalid, it remains invalid permanently. Your revalidate() method tries to reconcile the state of the object, doing whatever processing or cleanup it needs to return the object to a valid state. This reconciling of the object can either always succeed, sometimes succeed (and either throwing ValidityException or doing something else in case of failure), or never succeed (also achievable just by not overriding revalidate(), which will throw ValidityException).
Defined in the validate.h header file.
class MoneyAccount : public
ValidatedObject
{
private:
// if less than 0 money left, we're broke -->
object corrupted!
// (must then see MoneyAccount manager to
revalidate() or go to jail:P)
// (in this example though, once you're in
debt, your account is frozen!)
double balance;
public:
MoneyAccount(unsigned double initialDeposit) :
ValidatedObject(), balance(initialDeposit) { }
// should be able to see balance even if
account is frozen!
double GetBalance() { return balance; }
// account only valid if not in debt!
virtual bool valid()
{
// if we know the object is
invalid from a previous error,
// object is still invalid (in
this case, account still frozen)
if (!ValidatedObject::valid())
return
false;
// freeze account by invalidating
object if in debt
if (balance < 0)}
{
invalidate();
return
false;
}
else
return
true;
}
// these operations work only if the account is
not frozen
void deposit(unsigned double amt)
{
validate(); // call to
validate will throw if object not valid
balance += amt;
}
double withdraw(unsigned double amt)
{
validate(); // call to
validate will throw if object not valid
// can withdraw up to how much we
have left in the account
double amtWithdrawn = (balance
- amt >= 0 ? amt : balance);
balance -= amtWithdrawn;
return amtWithdrawn; //
return actual amount withdrawn
}
// called by creditors to make bank pay!
Account could get frozen here!
// assume bank always pays creditors even if
account is frozen
// calls to any other MoneyAccount methods
should properly discover
// any new debt and thus freeze account
void pay_creditors(unsigned double amt) {
balance -= amt; }
};
void IWillThrow()
{
// create account and then perform some
transactions
MoneyAccount acct(200.00);
acct.deposit(700.00);
acct.withdraw(550.00);
// uh oh ... now creditors take my money away,
my account is frozen
acct.pay_creditors(1000);
// now trying to do something with my frozen
account will throw ValidityException
acct.withdraw(50.00);
}
int main()
{
try
{
// call our method which
throws
IWillThrow();
}
catch (RootException &ex)
{
// can also say: cout
<< ex << endl;
// operator<<() for
RootExceptions just streams out what()
cout << ex.what()
<< endl;
}
return 0; // won't reach here ... exception
thrown above
}
None.
None.
Member | Where defined | Description |
---|---|---|
enum Validity { INVALID = 0, VALID = 1 }; | ValidatedObject | Enumerated type. Is this object valid or not? INVALID means object is in an invalid state. VALID means object is in an valid state. |
enum Revalidation { NONE_TRIED = 0, REVALIDATE_FAILED = 1 }; | ValidatedObject | Enumerated type. Flag passed to ValidityException when its thrown indicating whether the failure occurred on an unsuccessful revalidation attempt. |
ValidatedObject() | ValidatedObject | Default constructor. Initially, the object is in a VALID state. |
Validity GetValidity() | ValidatedObject | Return the state of the object as a Validity value. |
virtual bool valid() | ValidatedObject | Returns whether the object is in a valid state.To define the critieria used to define whether the object is in a valid state or not, override this method. Often, in your valid() method, you may wish to test whether the object is already valid to save some work as no further testing is required if the object is found to already be invalid. |
virtual void invalidate() | ValidatedObject | Invalidate this object by changing the state to INVALID. You can override this method if your class needs to also set some other flags or doing some other processing when it becomes INVALID. |
virtual void validate() | ValidatedObject | Validates the object by calling valid(). If the object is an invalid state, throws a ValidityException. You can override this method if your class needs to also set some other flags, needs to do some other processing at validation time., or you want other behavior than an exception being thrown when the object proves to be INVALID. You can choose whether any of your object's method needs to validate the object or not by calling validate()at the beginning of the method (or at any other time in the method) if you wish to validate the object's state before proceeding. If a method does not need validation because you wish to force the operation to succeed (even if the object is in an INVALID state), just don't call validate(). |
virtual void revalidate() | ValidatedObject | Attempts to revalidate the object by trying to reconciling its internal state. Unless you override the revalidate() method, once an object becomes invalid, it remains invalid permanently and all validated methods will throw a ValidityException. Your revalidate() method tries to reconcile the state of the object, doing whatever processing or cleanup it needs to return the object to a valid state. This reconciling of the object can either always succeed, sometimes succeed (and either throwing ValidityException or doing something else in case of failure), or never succeed (also achievable just by not overriding revalidate(), which will throw ValidityException). |
None.
RootException,
ValidityException.
Copyright © 2002, Michael Gradman and Corwin Joy.
Permission to use, copy, modify, distribute and sell this software and its documentation for any purpose is hereby granted without fee, provided that the above copyright notice appears in all copies and that both that copyright notice and this permission notice appear in supporting documentation. Corwin Joy and Michael Gradman make no representations about the suitability of this software for any purpose. It is provided "as is" without express or implied warranty.