allocator_traits::construct() vs allocator_traits::allocate()

There are two techniques to do this depending on what you have at the moment.

If you have an lvalue expression, say the value field in a node, then you can use std::addressof like so:

allocator_traits<allocator_type>::construct(alloc, std::addressof(ptr->value), ...);

where ptr is an allocator_type::pointer.

However if you don't have a field to dereference and you want to convert an allocator_type::pointer to T*, there's a trick you need to implement first:

template <class T>
inline
T*
to_raw_pointer(T* p) noexcept
{
    return p;
}

template <class Pointer>
inline
typename std::pointer_traits<Pointer>::element_type*
to_raw_pointer(Pointer p) noexcept
{
    return p != nullptr ? ::to_raw_pointer(p.operator->())
                        : nullptr;
}

And now you can say:

allocator_traits<allocator_type>::construct(alloc, to_raw_pointer(ptr), ...);

Starting with C++20, there is std::to_address, proposed in P0653.