Provide a minimal standard compliant allocator.
More...
Namespaces |
namespace | bsltf |
Detailed Description
- Outline
-
-
- Purpose:
- Provide a minimal standard compliant allocator.
-
- Classes:
-
- See also:
- Component bsltf_stdtestallocator
-
- Description:
- This component provides an allocator,
bsltf::StdStatefulAllocator
, that defines the minimal interface to comply with section 17.6.3.5 ([allocator.requirements]) of the C++11 standard, while still providing an externally visible and potentially distinct state for each allocator object. This type can be used to verify that constructs designed to support a standard-compliant allocator access the allocator only through the standard-defined interface.
StdStatefulAllocator
delegates its operations to the allocator passed at construction (or the default allocator if no allocator is passed) that is also the sole attribute of this class. In most tests, a bslma::TestAllocator
will be passed.
- The key differences between this test allocator and a regular BDE allocator are:
-
This allocator does not support the
scoped
allocation model, so that elements in a container will often have a different allocator to the container object itself.
-
This allocator may propagate through copy operations, move operations and
swap
operations, depending on how the template is configured as it is instantiated.
-
- Usage:
- This section illustrates intended use of this component.
-
- Example 1: Testing The Support for STL-Compliant Allocator:
- In this example we will verify that a type supports the use of a STL-compliant allocator.
- First, we define a simple container type intended to be used with a C++11 standard compliant allocator:
template <class TYPE, class ALLOCATOR>
class MyContainer {
ALLOCATOR d_allocator;
TYPE *d_object_p;
public:
MyContainer(const TYPE& object, const ALLOCATOR& allocator);
~MyContainer();
TYPE& object();
const TYPE& object() const;
};
Then, we define the member functions of MyContainer
:
template <class TYPE, class ALLOCATOR>
MyContainer<TYPE, ALLOCATOR>::MyContainer(const TYPE& object,
const ALLOCATOR& allocator)
: d_allocator(allocator)
{
d_object_p = d_allocator.allocate(1);
new (static_cast<void *>(d_object_p)) TYPE(object);
}
template <class TYPE, class ALLOCATOR>
MyContainer<TYPE, ALLOCATOR>::~MyContainer()
{
d_object_p->~TYPE();
d_allocator.deallocate(d_object_p, 1);
}
template <class TYPE, class ALLOCATOR>
TYPE& MyContainer<TYPE, ALLOCATOR>::object()
{
return *d_object_p;
}
template <class TYPE, class ALLOCATOR>
const TYPE& MyContainer<TYPE, ALLOCATOR>::object() const
{
return *d_object_p;
}
Now, we use bsltf::StdStatefulAllocator
to implement a simple test for MyContainer
to verify it correctly uses a parameterized allocator using only the C++11 standard methods: bslma::TestAllocator oa("object", veryVeryVeryVerbose);
{
typedef MyContainer<int, bsltf::StdStatefulAllocator<int> > Obj;
Obj mX(2, bsltf::StdStatefulAllocator<int>(&oa));
const Obj& X = mX;
assert(sizeof(int) == oa.numBytesInUse());
assert(X.object() == 2);
mX.object() = -10;
assert(X.object() == -10);
}
assert(0 == oa.numBytesInUse());