 
 
 Widening Object References
Widening Object References Narrowing Object References
Narrowing Object References 
Consider the following outline of IDL interface definitions:
interface Account {
. . . 
};
interface Savings: Account {
. . .
};
This outline results in the definition of C++ data types Account, Savings, Account_ptr, Account, Account_var, Savings_var, and Savings_ptr. 
To show the assignment compatibility between the last four of these types, assume the following four definitions:
Account_ptr pa = ...; Account_var va = ...; Savings_ptr psa = ...; SavingsLvar vsa = ...;
As is normal in object-oriented systems, if you have a reference to a Savings object, you can assign it to a reference of type Account. Moving from a derived interface to a base interface is termed widening in CORBA (C++ refers to this as upcast).
The following assignments automatically widen a reference from a Savings reference to an Account reference (read these assignment statements independently, not as a statement sequence):
pa = psa;     //Allowed but no reference count increment.
pa = vsa;     //Allowed but no reference count increment.
va = psa;     //Allowed but no reference count increment.
              //Reference count of va is decremented.
va = Account::_duplicate(vsa);
Note: 
It is a compile-time error to write va = vsa; such implicit widening between _var types is illegal in the CORBA specification.
To increment the reference counts in the first three assignments, the _duplicate( ) function should be used:
pa = Account::_duplicate(psa); // Reference count incremented. pa = Account::_duplicate(vsa); // Reference count incremented. va = Account::_duplicate(psa); // Reference count incremented. // Reference count of object va // previously pointed to is // decremented.
The term narrowing is used in CORBA when moving from a base interface to a derived interface (C++ refers to this as down-cast). If you have a base interface reference, you can assign it to a derived interface, but only if the base reference actually refers to an instance of the derived interface. There is no way to statically determine whether this condition holds, so a runtime test must determine the safety of the assignment.
The following statements narrow a reference from an Account reference to a Savings reference (read these if statements independently, not as a statement sequence):
psa = Savings::_narrow(pa); 
if (!CORBA::_is_nil(psa))
{  /* pa did reference a Savings */ }
else
{ /* the narrow failed */ }
psa =Savings::_narrow(va);
if (!CORBA::_is_nil(psa))
{ /* va did reference a Savings */ }
else { /* the narrow failed */ )
vsa = Savings::_narrow(pa); 
if (!CORBA::_is_nil(vsa))
{ /* va did reference a Savings */ }
 else 
{ /* the narrow failed */ }
Note that the static function _narrow( ) returns a nil object reference if the parameter passed to it is not a reference to an object of the correct interface, or a derived interface. A successful call to _narrow( ) increments the reference count of the target object; a failed call does not.
