簡體   English   中英

解引用STL集的迭代器

[英]dereferencing iterator of STL set

我在從STL集繼承時遇到問題(我認為):

這是Prime類:

class Prime : public set<A> {
private:
  // private data members.
public:
  // C'tor...
  void printParticularA(const int& id);
}

這是A類:

class A : public List<B>{  
private:  
  // data members.  
  int id;
public:  
  // C'tor  
  A(const A& copy) : List<B>(copy), //copy data members  
     { // validate data and throw exceptions if needed. };

  bool operator< (const A& rhs) const{  
    return id < rhs.id;  
  }

  void printReport() const {  
    for(const B& item : *this){ item.print(); }
  }

}

現在這是問題所在。 在下一個函數中,我要在集合中打印特定的A對象:

void Prime::printParticularA(const int& id) {
  find(AFinder(id))->printReport();
}

我也試過這個:

void Prime::printParticularA(const int& id) {
  *(find(AFinder(id))).printReport();
}

注意:假設類B具有print()方法。
note2:AFinder是用於僅使用id數據制作虛擬A對象的類。

問題是,當“查找”找到對象時,它會返回const_iterator(因為set中的每個對象都是const),而當我取消引用它時,我會得到該對象的副本(??),但其中的B列表為空!
'->'版本也會發生這種情況。

現在我知道set不允許我更改對象,但我不打算更改對象(如在printReport成員函數的聲明中所見)。

我對此表示感謝!

編輯:謝謝大家,您為我提供了很多幫助,尤其是學習了不要做的事情。
我解決了這個問題,但這里沒有列出,列出或列出任何我的課程。
我的錯誤是在理解我給出的問題(是的,這是我的作業,我還是c ++的新手)。
對不起,如果您覺得我浪費了您的時間。
我希望我能從您的所有經驗中學習,有一天能幫助他人!
總之,謝謝! :)

您的代碼到處都是混亂的。 這個問題看起來並不直接與set或Iterator綁定,而是完成了一般的壞事。

對於初學者來說,請使您的op <const並永久刪除副本ctor -股票庫應該可以正常工作。 使用set的內部查找來搜索並查看是否找到了項。

所有這一切都可能使您描述的問題消失,如果沒有,請發布一個完整的可編譯示例,其中包含您所看到和所期望的正確文本。

盡管您尚未包括List的實現,但是問題很可能在那里。 更精確地說,可能會破壞Listbegin()end()成員函數。 它們返回的值可能相同(或無效),從而導致基於范圍的for循環不執行任何操作。 當然,這是基於您的set::find返回一個有效的迭代器,而不是結束迭代器。

以下示例是您問題中代碼的修改。 它使用std::list而不是List ,並且不使用AFinder因為您尚未包含其代碼。

#include <set>
#include <list>
#include <iostream>

struct B
{
    int id_;
    explicit B(int id) : id_(id) {}
    void print() const
    {
        std::cout << "B::id = " << id_ << std::endl;
    }
};

class A : public std::list<B>
{
public:
    explicit A(int id) : id_(id) {}

    bool operator<(const A& rhs) const
    {
        return id_ < rhs.id_;
    }

    bool operator==(const A& other) const
    {
        return id_ == other.id_;
    }

    void printReport() const
    {  
        for(auto& item : *this)
        {
            item.print();
        }
    }

private:  

    // data members.  
    int id_;

};


class Prime : public std::set<A>
{
public:

    void printParticularA(const int& id)
    {
        std::cout << "finding " << id << std::endl;
        auto el = find(A(id));
        if(el == cend())
        {
            std::cout << "not found" << std::endl;
        }
        else
        {
            find(A(id))->printReport();
        }
        std::cout << "done finding " << id << std::endl;
    }
};


int main()
{
    Prime p;

    A   a1(1);
    a1.push_back(B(1));
    a1.push_back(B(2));
    a1.push_back(B(3));
    p.insert(a1);

    A   a2(2);
    a2.push_back(B(4));
    a2.push_back(B(5));
    a2.push_back(B(6));
    p.insert(a2);

    p.printParticularA(1);

    p.printParticularA(2);

    // doesn't exit
    p.printParticularA(3);
}

這將產生以下輸出。

發現1
B :: id = 1
B :: id = 2
B :: id = 3
找到1
發現2
B :: id = 4
B :: id = 5
B :: id = 6
找到2
發現3
未找到
找到3

您的代碼確實違反了許多C ++規則。 您為什么不嘗試這樣:

#include <iostream>
#include <list>
#include <map>

using namespace std;

class SimpleInt {
public:  
  int data_;

  SimpleInt(const int data): data_(data) {};
  void print() const {cout << data_ << " ";};
};

template <typename T>
class A {  
private:  
  // private data members.  
public:  
  list<T> list_of_B_; // this is for simlicity. Make getters as you need
  const int id_; // delete it or copy to map. You sholdn't change it.

  A(int id) : list_of_B_(), id_(id) {} 
  A(const A<T>& copy) : list_of_B_(copy.list_of_B_), id_(copy.id_) {} //copy data members  
  A(A<T>&& copy) : list_of_B_(::std::move(copy.list_of_B_)), id_(copy.id_) {} //move data members  

  void printReport() const {  
    for(const T& item : list_of_B_){ item.print(); }
  }

};

template <typename T>
class Prime {
private:
  // private data members.
public:
  // The main difference with your source
  map<int, T> map_of_A_; // this is for simlicity. Make getters as you need
  // C'tor...
  void printParticularA(const int& id) {
    auto it = map_of_A_.find(id);
    if (it != map_of_A_.end())
      it->second.printReport();
  }
};

int _tmain(int argc, _TCHAR* argv[])
{
  typedef A<SimpleInt> ASimpled;
  Prime<ASimpled> prime;
  ASimpled a(1);
  a.list_of_B_.push_back(SimleInt(1));
  a.list_of_B_.push_back(SimleInt(2));
  a.list_of_B_.push_back(SimleInt(3));
  ASimpled b(2);
  b.list_of_B_.push_back(SimleInt(10));
  b.list_of_B_.push_back(SimleInt(20));
  b.list_of_B_.push_back(SimleInt(30));
  prime.map_of_A_.insert(make_pair(a.id_, a));
  prime.map_of_A_.insert(make_pair(b.id_, b));

  prime.printParticularA(2);

return 0;
}

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM