2016-01-15 6 views
5

std::uses_allocator<T, inner_allocator_type>::value==true場合、私はここにいくつかの単語http://en.cppreference.com/w/cpp/memory/scoped_allocator_adaptor/constructのstd :: scoped_allocator_adaptorとクラス:: allocator_arg_t

を見つける(タイプ Tはアロケータを使用して、例えば、それはコンテナである)

そして std::is_constructible<T, std::allocator_arg_t, inner_allocator_type, Args...>::value==true

はその後

std::allocator_traits<OUTERMOST>::construct(OUTERMOST(*this), 
              p, 
              std::allocator_arg, 
              inner_allocator(), 
              std::forward<Args>(args)...); 
を呼び出す場合私も use_argを置き換えるために use_aを書く210

だから、私は簡単なテスト

struct use_arg { 
    template <typename Alloc> 
    use_arg(std::allocator_arg_t, Alloc &, int i) 
     { std::cout << i << " in use_arg()\n"; } 
}; 

namespace std { 

template <typename A> struct uses_allocator<use_arg, A>: true_type {}; 

} // namespace std 

void test_scoped() 
{ 
    std::scoped_allocator_adaptor<std::allocator<use_arg>> sa; 
    auto p = sa.allocate(1); 
    sa.construct(p, 4); 
    sa.destroy(p); 
    sa.deallocate(p, 1); 
} 

を行うが、gccと打ち鳴らすは私にこれらのエラーhttps://gist.github.com/anonymous/3e72754a7615162280fb

を与えます。それは正常に実行することができます。

struct use_a { 
    template <typename Alloc> 
    use_a(int i, Alloc &) { std::cout << i << " in use_a()\n"; } 
}; 

これらの動作はどうなりますか?

答えて

3

私はlibstdC++とlibC++の両方が、標準がOPの例に必要としているものを正確にやっていると思います。

uses_allocator<use_arg, allocator<use_arg>>は本当ですが、use_argは右辺値アロケータから構築可能ではないので、constructコールが悪い形成する必要があるためis_constructible<use_arg, allocator_arg_t, inner_allocator_type, int>はfalseです。

しかし、私はそれが標準の欠陥だと思う。このタイプを考えてみましょう:

struct use_arg { 
    using allocator_type = std::allocator<use_arg>; 
    use_arg(allocator_type&&) { } 
}; 

uses_allocatoris_constructible特性の両方の真のですが、scoped_allocator_adaptor::construct(pointer)への呼び出しは、コンパイルに失敗します。

is_constructible<T, inner_allocator_type>(左辺値)はinner_allocator_type&を渡しますが、これは標準では言いますが、それは右辺アロケータからの構築をテストするのに矛盾します。

1

問題は、参考としてAllocを受け取ったことです。

std::is_constructible<T, std::allocator_arg_t, inner_allocator_type, Args...>::value==true 

ここにあなたのケースでinner_allocatorはちょうどstd::scoped_allocator_adaptor<std::allocator<use_arg>> あり、それはstd::scoped_allocator_adaptor<std::allocator<use_arg>>&に変換することはできません。値でAlloc、またはconst-referenceで受け取ることができます。

+0

'std :: is_constructible >> :: value'はどうでしょうか?それはまた「偽」ですが、構築することができます。 – linux40

+0

@ linux40これはバグのように見えます。たとえば、clangではこのチェックはなく、uses_allocator :: valueだけがチェックされています。 – ForEveR

+0

gccにはチェックが1つしかありません。 – ForEveR

関連する問題