The ranged type class template is defined approximately as:
template<class T, T MIN, T MAX, class TR = ranged_traits<T, MIN, MAX> > class ranged_type;
Where T is the base type, MIN and MAX define the range, and TR defines a
traits class. The
traits class defines various members to control the behavior of various aspects of the class, such as what is to be done upon detecting an overflow condition. The default of which is to throw an exception.
I said the class template is approximately defined as above because there are additional template parameters that are defaulted. These are defined by the implementation and are used for class specialization. These parameters are defined from members of the
traits class, and allow classes to be instantiated with or without explicit constructors taking primitive type arguments, and/or cast operators to primitive types. The default is the safest, having explicit constructors and no cast operator. Assignment, arithmetic, relational, and equality operators are defined for the class. These are defined for every combination of the ranged type class and its intermediate types. Intermediate types hold the result of arithmetic operations and keep track of the maximum number of digits.
Mixing constants and variables of primitive types in expressions with ranged types is problematic. At issue is determining at compile-time the number of digits in the value. Obviously, the number of digits in an integral constant expression (ICE) can be calculated at compile-time, but the C++ language does not allow an operator to be overloaded based on that. The very nature of a variable makes it impossible to determine its number of digits at compile-time. Casting the value to the ranged type is one way to use it in an expression. There are two possible problems with this: 1) it can be inefficient because it causes additional range checks to be done, and 2) the value may exceed the range. To compensate for this, two templates are defined,
variable, that convert values to the range type's intermediate type. Their use will lead to expressions that are harder to read, but can be more efficient to execute.