0

Holderマップの値のみを公開するクラスがあります。そのために変換イテレータを使用しました。型 (ClassA*) への単純なポインターを使用しても機能しますが、unique_ptr では機能しません。このコードに基づいて次の例を作成しました: transform_iterator compile problem

次のエラー (begin()関数に由来する) が表示されます。これは、誰かが参照を使用する代わりにペアをコピーしようとしていると思われます。

前もって感謝します

エラー C2248:
' std::unique_ptr<ClassA,std::default_delete<_Ty>>::unique_ptr':クラス ' '
で宣言されたプライベート メンバーにアクセスできません
std::unique_ptr<ClassA,std::default_delete<_Ty>>

#include <iostream>
#include <map>
#include <functional>
#include <memory>
#include <string>
#include <boost/iterator/transform_iterator.hpp>

struct ClassA
{
    ClassA( const std::string& strName ) : m_strName( strName ) {}
    std::string m_strName;
};

template <typename K, typename V>
const V & get_value(std::pair<K, V> const & p)  { return p.second; }

class Holder
{
    typedef std::map<int, std::unique_ptr< ClassA > > TMap;
    typedef std::unique_ptr< ClassA > UniqueA;
    TMap m_Map;
public:
    Holder()
    {
        UniqueA a( new ClassA( "#2# ") );
        UniqueA b( new ClassA( "#3# ") );
        UniqueA c( new ClassA( "#4# ") );
        m_Map.insert( std::make_pair( 2, std::move( a ) ) );
        m_Map.insert( std::make_pair( 3, std::move( b ) ) );
        m_Map.insert( std::make_pair( 4, std::move( c ) ) );
    }
    typedef std::function< const TMap::mapped_type & (const TMap::value_type &) > F;
    typedef boost::transform_iterator<F, TMap::iterator> transform_iterator;

    transform_iterator begin()
    {
        return boost::make_transform_iterator(m_Map.begin(), &get_value< int, std::unique_ptr< ClassA > >);
    }
    transform_iterator end()
    {
        return boost::make_transform_iterator(m_Map.end(), &get_value< int, std::unique_ptr< ClassA > >);
    }
};

void MyTest()
{
    Holder bla;
    auto s_beg = bla.begin();
    auto s_end = bla.end();
    for( auto t=s_beg; t!=s_end;++t) {
        std::cout << ( *t )->m_strName << std::endl;
    }
}
4

1 に答える 1

2

問題はget_value、 へのpair<K,V>参照を受け取るが、マップの値の型である への参照が渡されていることpair<const K,V>です。これには変換が必要で、キーと値の両方を新しいペアにコピーする必要があります。unique_ptrコピーできないため、エラーが発生します。

解決策 1: matchget_valueへの参照を受け入れるように変更します。これにより、関数はマップの値への参照を直接受け入れることができます。pair<const K,V>TMap::value_type

解決策 2: ;ではなくget_valuefor をインスタンス化する これは、ソリューション 1 と同じ効果があります。const intint

解決策 3:ではなくget_valuefor をインスタンス化して、マップの値への参照を含むペアを取得します。この一時的なペアは、 をコピーせずに作成できます。const unique_ptr &unique_ptrunique_ptr

于 2013-06-04T10:13:03.487 に答える