2008-08-18

Concept厳格すぎワロタwww

例えば次のコードで、

template < typename T >
void g( T x ) { }

template < typename T > requires Foo< T >
void f( T x )
{
    g( x ) ;
}

コンセプトFooを記述したいとする。次のように書くのは誤りである。

auto concept Foo < typename T >
{
    requires std::CopyConstructible< T > ;
}

なぜならば、この型を引数として、関数gを呼んでいるからだ。当然、関数gもコンセプトで要求しなければならない。

auto concept Foo < typename T >
{
    requires std::CopyConstructible< T > ;
    void g( T ) ;
}

さて、この時点でもう厳格すぎて嫌になる人間と、そうでない変態がいる。そういう変態は、今は主にBoost界隈に生息しているが、いずれC++0xに移住してくるだろう。そのような変態のためには、続きがある。もし、関数fが次のようであったならば、どのようにコンセプトFooを記述すればよいのだろうか。

template < typename T > requires Foo< T >
void f( T x )
{
    std::cout << x << std::endl ;
}

このコンセプトを苦もなく書けるならば、真の変態と自称してよい。答えは次のとおり。

auto concept Foo < typename T >
{
    requires std::CopyConstructible< T > ;
    std::ostream & operator << ( std::ostream &, T & ) ;
}

なお、このコードに対するConceptGCCのエラーがひどく読みづらい。まだ改善の余地ありだ。VC++のように、typedefされた型名で出力すれば、少しはマシになるのだが。

No comments: