2009-03-19 7 views
3

マップされたデータを入力順にトラバースできるようにするコードを記述しました。カスタムSTLコンテナ

私はコード化されたソリューション時代のカップルがいた:

考えるとキータイプ、K、およびデータ・タイプ、D、 のstd ::マップ のstd ::ベクトル

1がランダムにしたかったですデータエントリを検索するには、map.find(K)を使用します。エントリ順に地図をたどりたいときは、std::vector::iterator (begin(), end()]を使います。

これは問題ありませんでしたが、練習として、'OrderedMap'をSTL準拠のコンテナとして書きたいと思いました。私は(この議論にストリップダウン)もあります:

template <typename K, typename D> 
class OrderedMapValue 
{ 
private: 
    K first_ref; 
    std::map<K,size_t>& m; 
    std::vector<D>& v; 
public: 
    const K& first 
    D& second 
    assignment operator=(const D& data) 
    { 
     std::map<K,size_t>::const_iterator iter = m.find(first_ref); 
     v[iter.second] = data; // error checking of iter stripped 
    } 
}; 

は、さらに次のコードは動作します

template <typename K, typename D> 
class OrderedMap 
{ 
public: 
    typename OrderedMapValue<K,D>& OrderedMap<K,D>::operator[](const K&); 
    // snip... 
}; 

class MyClass 
{ 
public: 
    MyClass(std::string s) : _my_data(s) {} 
private: 
    std::string _my_data; 
}; 

を仮定:

OrderedMap<std::string,MyClass*> omap; 
omap["MyKey"] = new MyClass("dummy"); 

しかし、このコードがない:

OrderedMap::iterator iter = omap.find("MyKey"); 
MyClass * obj = iter->second; 
delete obj; 
iter->second = new MyClass("dummy"); 

私はドンe何か a)構造的に愚かであるか b)不必要に複雑ですが、これはどのように行うべきですか?

私はここで車輪を再発明する可能性が高いと認識していますが、この努力は主にSTL容器、そのデザインパターン、および適切な使用についての私の知識を増やすことです。任意の洞察力を事前に

おかげで、OrderedMapValue::operator=

+0

> second? 'iter'は' OrderedMap :: iterator'で '* iter'は' OrderedMapValue'ですか? –

+0

それは正しい答えです。 –

+0

あなたは正しいです、私はあなたの答えを受け入れました。概念的には、あなたは本当に必要なものの本質を釘付けにしました。 TYPE&演算子[]メソッドを詳しく見てみると、受け入れられた解決策としてマークされたコードが人を誤解させないように、アイロンがけされる必要があるいくつかの問題があることがわかりました。 私の(良い)意図は実績のある解決策を提供することでしたが、私は今これに戻ります。 –

答えて

0

は、あなたが持っている:

std::map<K,size_t>::const_iterator iter = m.find(first_ref); 

first_refとは何ですか?コードは他の場所でそれを参照しません。それは、それが公共のメンバーによって他の場所に置き換えられた古い実装の痕跡かもしれないように私に見える。

const K& first

これが問題になりますか?

EDITコメントから:first_refがどこにでも初期化されていることを示すコードは表示されません。私が知る限り、m.find(first_ref)の呼び出しは、OrderedMapValueのキーではなく、空の文字列を検索しています。

+0

first_refは、OrderedMapValueの非constプライベートメンバーです。私は最初のconstを維持しようとしていましたが、依然としてキーメンバーを設定する手段を提供しています。 –

+0

しかしfirst_refはどこで初期化されていますか?私が言うことができるのは、 m.find(first_ref)が上書きしている文字列ではなく空の文字列を検索していることです。 –

+0

Dan、 コードを簡潔にするために、私は必要なコードを編集しました。後見では、この議論のために必要でなかったので、その詳細を残しておくべきでしょう。 –

2

私はこれをテストするために、今のコンパイラを持っていないので、エラーが発生する可能性があり、私はあなたがそれをもっとしたいと思います:イテレータの使用量は、 `iter-すべきではない

template <typename K, typename D> 
class OrderedMap 
{ 
private: 
     std::map<K,size_t> &m; 
     std::vector<D> &v; 
public: 
    typename pair<K,D> TYPE; 

     TYPE& operator[](const K &k) 
    { 
     return v[ m[ k ]]; 
    } 

    TYPE& operator[](size_t idx) 
    { 
     return v[ idx ]; 
    } 

    pair<iterator,bool> insert(const TYPE& pair) 
    { 
     map<K, size_t>::const_iterator iter; 
     iter = m.find(pair.first); 

     if(iter != m.end()) 
      return make_pair(v[ iter.second], false); 

     m.insert(make_pair(pair->first, v.size())); 
     v.push_back(pair->second); 

     return make_pair( v.last() , inserted); 
    } 

    iterator &begin() 
    { 
     return v.begin(); 
    } 
    // etc 
}; 
+0

はい、それは私が探していたものです。サンプルを提供するのに感謝します。 –

+0

'OrderedMap'はマップとベクトルを参照ではなく値で保持する必要があります。 'TYPE'はmapの動作に合わせて、おそらく' pair 'でしょう。また、おそらく 'operator [](const K&)が' D& 'を返すことを望んでいます。 –

関連する問題