C++ Container With Conditionally Protected Access
By: Pavel Horbonos, Midvel Corp
Tags: Containers, Software Engineering, Cplusplus, Programming, Software Development

When we talk about the processing of the container’s content, we mean two situations. The first one is an iterator with full access to read and change the elements of the container. The second one is the constant iterator which has no right to change the content. Though what if we need to change the value of an element, but have to keep some condition on it?

Let’s see an example. We have a simple array-based container, which should keep only values from the interval [0, 1] . If we start with the simplest form of changing the content — index access operator (or random-access operator or indexator), at some moment we have to watch the next picture:

So you can simply imagine the same picture for the iterator and the dereference operator.

Why should we do that?

It is the moment you should say: “Hey, just add the specialized setter method with the built-in condition and the work is done!”. Okay, but I suppose that we are good developers and want to create a container compatible with STL requirements, with all matching iterators and operators. Even if no, you still need some tool to process every element, so there is no way to avoid an iterator development.

You may point on several alternatives.

a very fancy template, which will prevent the assignment of inappropriate values. The negative result is that the “bad” cases won’t compile. And, I believe, we may get a practically unreadable template.

a specialized class with a proper data type. You will be happy to get a lot of work with the new hierarchy, type conversions, assertions, specific constructors and so on.

an external condition. We won’t even discuss this idea, because you can imagine the problems of scaling, reusing and porting of such code.

All we need is a simple, perfectly compiled and conversions free solution.

Proxy class

Okay, we will need an additional class. Though, it is not a new data type, as we discussed earlier. This class will be a part of our container and will represent a lightweight wrapper to keep the reference to the instance and the method with the condition to be checked. Somehow it may remind the proxy class for the bool vector.

The idea is very simple:

Container’s overloaded operators return the reference to a one-time proxy-object; Proxy-object takes the desired value and checks the condition; If the check is passed — provide the value inside the container.

Since the idea is very simple, we can now provide a code:

Implementation is simple, you may only want to add more arithmetical operators’ overloads. As you may notice, we also added the property operator for the quick conversion into the basic container type. Also, you can implement any condition, checking policy, exceptions generation and so on. As an example I followed the idea of IntervalContainer , so all upper values are saved as 1 and all lower values are saved as 0.

Indexator

We have already seen the code of how we want it to work, so now I’ll show you the implementation. It is an operator overload, which returns a proxy object which wraps the real element access. To dismiss problems with the conversions, we separate the read-only access and write-access.

You may notice, that all the functionality is kept in the proxy-class and it gives a lot of flexibility and portability to the code. We can simply imagine the PImpl idiom, with the condition check kept in the descendant proxy classes.

Iterator

We want the next code to compile and work:

As you may understand it is the time for the iterator implementation. In general, logic is the same as with the indexator overload: return an object of proxy-class with some restrictions.