Re: использовать аллокатор только для тех типов, которые это
От: Кодт Россия  
Дата: 13.03.14 12:04
Оценка: 9 (1) +1
Здравствуйте, niXman, Вы писали:

X>более полный пример:

X>
X>template<typename Alloc>
X>struct type {
X>   type(Alloc &alloc)
X>      :alloc(alloc)
X>   {}

X>   void some_func(const char *ptr, const std::size_t size) {
X>      archive ia(ptr, size, alloc);
X>      type0 arg0;
X>      type1 arg1;
X>      ia & arg0
X>         & arg1;
X>      func(arg0, arg1);
X>   }

X>private:
X>   Alloc &alloc;
X>};
X>

X>тут, обратите внимание на type0/type1 и arg0/arg1.

Обратил, ну и где там аллокатор?
Предполагалось, что должно быть
X>   void some_func(const char *ptr, const std::size_t size) {
X>      archive ia(ptr, size, alloc);
X>      type0 arg0;        // не знает про аллокатор
X>      type1 arg1(alloc); // использует аллокатор
X>      ia & arg0
X>         & arg1;
X>      func(arg0, arg1);
X>   }


Да?

Делаем вот так
with_allocator<type0, Alloc> arg0(alloc);
with_allocator<type1, Alloc> arg1(alloc);
ia & *arg0
   & *arg1
   ;
func(*arg0, *arg1);

где
template<class T, class A, bool WithA> struct with_allocator_base;

template<class T, class A> struct with_allocator_base<T,A,true>
{
  T var;
  explicit with_allocator_base(A& a) : var(a) {}
  T& operator() { return var; }
};
template<class T, class A> struct with_allocator_base<T,A,false>
{
  T var;
  explicit with_allocator_base(A& a) {}
  T& operator() { return var; }
};

template<class T, class A> struct with_allocator : with_allocator_base<T,A, has_constructor<T,A>::value >
{
  typedef with_allocator_base<T,A, is_constructible_from<T,A>::value > base;
  explicit with_allocator(A& a) : base(a) {}
};


Если типы копи-конструируемые, то можно и проще
template<class T, class A> auto make(A& a) -> enable_if< is_constructible<T,A>::value, T >::type { return T(a); }
template<class T, class A> auto make(A& a) -> enable_if<!is_constructible<T,A>::value, T >::type { return T( ); }

......

type0 arg0 = make<type0>(alloc);
type1 arg1 = make<type1>(alloc);
Перекуём баги на фичи!
 
Подождите ...
Wait...
Пока на собственное сообщение не было ответов, его можно удалить.