Saturday, July 23, 2005

BOOST extensions, and patterns for template specification

Among the BOOST initiative efforts for standardizing C++ libraries, one finds several other forms of activities, including techniques for meta-programming. One technique promotes more confusion by taking advantage of C preprocessor macro facility and the other abuses the weaknesses in the implementation of C++ templates.

The purpose of research in the design of a programming language is to facilitate the writing of understandable and correct programs. Existing loopholes that deviate from this principle must be recognized and avoided, not exploited.

Most C++ template implementations act like a word processor. Thus, the actual argument for a template parameter does not have to be a previously defined type. This behavior opens the door to all kinds of abuse. Furthermore, there is no mechanism in C++ to stipulate conditions on the set of allowable arguments.

The implementation of C++ templates follows the style of C macro definition. Thus, the instantiation of template parameters is an unregulated rewrite rule prior to parsing. Consider substituting template parameters with other templates. This creates a new template definition on the fly. As attractive as it may sound, one should consider the benefits of such dynamic definitions, especially in large programs. What kind of problem is solved towards better ways for software development to outweigh the damages resulting from its use?

The value of Abstract Data Types in the design and development of software is not open to dispute. The C++ template construct provides an elegant linguistic mechanism for defining an ADT. A means for specifying the set of permissible arguments for a template parameter will further improve the utility of this mechanism in creating reusable code. The following illustration shows how Z++ accomplishes this through a simple intuitive extension to C++.

In a template definition, the parameters like U and V in

template<type U, type V>

are combined within the definition. That is, the type arguments instantiating U and V do not have to be related in any way. Therefore, the specifications should be attached to each individual parameter. For instance, in

template<type U : spec_U, type V : spec_V>

the (optional) specification for each parameter follows the colon after that parameter.

In Z++ the construct for defining a specification for a template parameter is called a pattern. One possible pattern is the list of permissible types for instantiating the template parameter, like this.

pattern template<T> my_pattern
T : int, long;
end;

The identifier my_pattern is like the name of a class. It appears at where we put spec_U or spec_V in an earlier example. In this pattern we are limiting the range of types that can instantiate a template parameter, to int and long.

We can also specify the type of argument by listing the public methods that it must have. Here is an example.

pattern template<T> your_pattern
int operator+(void);
T some_method(double, const T);
void ?(T, int);
end;

The pattern your_pattern requires the instantiating type to include three public methods, an overloaded operator, a method named “some_method” and an unnamed method.

The T in the signature of a method is wild and will match any type. The question mark for the name of a method will match the first method with that signature, if there is one. Ideally, a pattern specification will be properly documented so a user understands the purpose of the methods in the pattern.

For an amusing recent development, without attempting to read the article, browse the new Proposal for Adding Modules to C++. Now take two minutes to read the entire article Namespace Extensions on how this has already been done and thoroughly tested

A moment of reflection reveals the value of years of research and experimentation prior to publicizing an achievement.

Labels: , ,