Polaris: ExtraInfo Class Reference

ExtraInfo Class Reference

a class for providing extra info to functions More...

#include <ExtraInfo.h>

Inheritance diagram for ExtraInfo:

Inheritance graph
[legend]
List of all members.

Public Member Functions

virtual ~ExtraInfo ()
virtual ExtraInfoclone () const =0

Detailed Description

a class for providing extra info to functions

Polaris C++ CVDL

See also:
ExtraInfo.h

ExtraInfo.h

Description

The ExtraInfo and Info classes work hand-in-hand.

Sometimes functions pointers are passed as parameters to other functions or to class objects with the intention of specifying some functionality. For instance, the Iterator class has an optional function parameter which allows one to specify certain conditions which an element of a Collection must pass in order for that element to be considered by the Iterator class.

In such cases, it is also often required that additional information be given to the passed-in function when it is called. The usual way of providing such information is by a void *, since it cannot be known what format that additional information should take.

Unfortunately, there is a hard-to-avoid memory leak problem with such an approach. For instance, if an Iterator is declared with such a procedure parameter, it is also given additional information (say, via a void *). This information may not be deleted by the Iterator since it has no idea how to delete the information. But it cannot necessarily be held statically by the creator of the Iterator, either, for instance by the method ProgramUnit::iterate(), since the information passed to the Iterator needs to be unique for each Iterator created. Therefore the additional information needs to be created on the stack, but since no one can delete it, the result is a memory leak problem. By the same token, even if it could be deleted, if the Iterator is copied, the additional information also needs to be copied, and again there is no way to know how to accomplish this.

The ExtraInfo/Info<t> classes are a simple solution to this problem by abstracting the 'void *' additional information into a class with copy and destruction properties. No other functionality is defined, with the intention that the derived template class Info<T> may be passed in as a parameter where an ExtraInfo is requested, thus giving as much flexibility as a 'void *' but with the desired copy and destruction semantics necessary for avoiding memory leaks.

Also, the addition of the class template Info<T> makes providing the necessary information a bit easier and more self-documenting.

Info<T>

Info<T> is a simple class template derived from Info which allows one to immediately specify the copy and destruction semantics needed by class ExtraInfo for any intrinsic C++ data structure, as well as any user-defined (struct, class, union, etc.) data structure in C++.

Examples

Example 1:

Suppose there exists a function

print_infix( const Tree &root, int (*func)(const Tree &root, const ExtraInfo &extra), const ExtraInfo &extra);

which prints in infix order all leaves 'leaf' of the Tree 'root' which match the criteria that (*func)(leaf, extra) returns 1.

Suppose further that you desire to write a function to have all leaves printed whose 'value' field is equal to the value 'my_value', which is provided as a parameter to the function. Then the following functions could satisfy this functionality:

void my_print(Tree &root, int my_value) { print_infix(root, my_print_condition, Info<int>(my_value)); }

int my_print_condition(const Tree &root, const ExtraInfo &extra) { return (root.value == ((Info<int> &)extra).data()); }

In this case, the ExtraInfo field is declared as a constant reference, since the question of destruction is easily solved. In other cases, the ExtraInfo field will be declared as an ExtraInfo object.

Example 2:

Suppose you have a class Iter:

class Iter { private: int _curr; ExtraInfo *_info; int (*_func)(int integer, const ExtraInfo &info); public: Iter(int (*func)(int integer, const ExtraInfo &info), const ExtraInfo &info) { _curr = 1; _func = func; _info = info.clone(); } ~Iter() { delete _info; } Iter(const Iter &other) { _curr = other._curr; _func = other._func; _info = other._info; } void operator ++ () { ++_curr; } int current() const { return _curr; } };

which iterates through all integers i from 1 to infinity which pass the additional test that (*func)(i, info) returns 1. Notice that the constructor and copy constructor are both able to clone the extra info without knowing what format it takes, and that the destructor is able to destroy the extra info as well.

In addition, it is desired that there be specific functions which return various versions of this Iterator by passing in different functions and extra data to the Iterator constructor. For example, the function

Iter iterate_multiples(int base);

should return an Iter which iterates on base, 2*base, 3*base, 4*base, ....

This could be set up simply as

int is_multiple(int integer, const ExtraInfo &info) { return (integer ((Info<int> &)info).data() == 0); }

Iter iterate_multiples(int base) { return Iter(is_multiple, Info<int>(base)); }

without worrying about who will delete the heap space. This is important because an automatic copying of an Iter object takes place upon the return from iterate_multiple(). Without the implicit semantics of copying and destroying which the call Info<int>(base) provide, this managing of the heap would be very difficult.

An example main program for this example is:

int main() { int j = 1; for (Iter i = iterate_multiples(10); j <= 1000; ++j, ++i) cout << i.current() << endl; }

OmegaInfo

Because, unfortunately, Info<void> is not useful, there is a special macro called OMEGA_INFO which is useful when you do not not need to pass in any extra info. Please see the manual page for OmegaInfo for more information.

Definition at line 193 of file ExtraInfo.h.


Constructor & Destructor Documentation

ExtraInfo::~ExtraInfo  )  [virtual]
 

Nothing to do

Definition at line 11 of file ExtraInfo.cc.


Member Function Documentation

virtual ExtraInfo* ExtraInfo::clone  )  const [pure virtual]
 

Implemented in Info< T >, and Info< int >.


The documentation for this class was generated from the following files:
 © 1995-2005 University of Illinois, Urbana-Champaign. All rights reserved.  Fri Mar 25 23:07:23 2005