本の虫

著者:江添亮
ブログ: http://cpplover.blogspot.jp/
メール: boostcpp@gmail.com
Twitter: https://twitter.com/EzoeRyou
GitHub: https://github.com/EzoeRyou

アマゾンの江添のほしい物リストを著者に送るとブログ記事のネタになる

筆者にブログのネタになる品物を直接送りたい場合、住所をメールで質問してください。

range-based forで固定回ループ

本の虫: Dwangoプログラミングコンテストの感想で固定回のループがあればいいと書いたが、range-based forにそういうイテレーターを与えてやればいいのではないかと気がついた。つまり、こういうことだ。

class counter_iterator
{

    std::size_t i ;

public :
    

    counter_iterator() : i(0) { }
    counter_iterator( std::size_t n ) : i(n) { }

    bool operator == ( const counter_iterator & rhs ) const
    {
        return i == rhs.i ;
    }

    bool operator != ( const counter_iterator & rhs ) const
    {
        return i != rhs.i ;
    }

    std::size_t & operator * ( )
    {
        return i ;
    }

    counter_iterator & operator ++ ()
    {
        ++i ;
        return *this ;
    } 
} ;

class nth_loop
{
private :
    std::size_t i ;

public :
    nth_loop( std::size_t n ) : i(n) { }

    counter_iterator begin() const
    {
        return counter_iterator() ;
    }

    counter_iterator end() const
    {
        return counter_iterator(i) ;
    }
} ;

nth_loop rep( std::size_t n )
{
    return nth_loop( n ) ;
}
 
int main()
{
    for ( auto elem : rep(10) )
    {
        std::cout << elem << std::endl ;
    }
}

とはいえ、for ( elem : 10 )と書きたいところだ。

追記:ユーザー定義リテラルを使う方法を思いついた。unsigned long long intに書き変えるのは省略。

nth_loop operator "" _( unsigned long long int n )
{
    return nth_loop( n ) ;
}

int main()
{
    for ( auto i : 10_ )
    {
        std::cout << i << std::endl ;
    }
}

だいぶ簡略化された。

なお、Boostに同等のライブラリ、boost::iragenがある。

ドワンゴ広告

ドワンゴは本物のC++プログラマーを募集しています。

採用情報|株式会社ドワンゴ

CC BY-ND 4.0: Creative Commons — Attribution-NoDerivatives 4.0 International — CC BY-ND 4.0