2012-02-06 37 views
6

Dưới đây là đoạn code mà gây ra lỗi:không có chức năng thành viên phù hợp cho cuộc gọi đến 'xóa'

Factory.h:

#include <string> 
#include <map> 

namespace BaseSubsystems 
{ 
    template <class T> 
    class CFactory 
    { 
    protected: 
     typedef T (*FunctionPointer)(); 
     typedef std::pair<std::string,FunctionPointer> TStringFunctionPointerPair; 
     typedef std::map<std::string,FunctionPointer> TFunctionPointerMap; 
     TFunctionPointerMap _table; 
    public: 
     CFactory() {} 
     virtual ~CFactory(); 
    }; // class CFactory 

    template <class T> 
    inline CFactory<T>::~CFactory() 
    { 
     TFunctionPointerMap::const_iterator it = _table.begin(); 
     TFunctionPointerMap::const_iterator it2; 

     while(it != _table.end()) 
     { 
      it2 = it; 
      it++; 
      _table.erase(it2); 
     } 

    } // ~CFactory 
} 

Và lỗi tôi nhận được:

error: no matching member function for call to 'erase' [3] 
         _table.erase(it2); 
         ~~~~~~~^~~~~ 

Bất kỳ lời khuyên? Cảm ơn.

+0

nhu cầu của 'it2' là gì? Làm thế nào về '_table.erase (it ++)'? – iammilind

Trả lời

7

Dưới đây là chữ ký của map::erase trong C++ 98:

void erase(iterator position); 

chức năng này có một iterator nhưng bạn đang đi qua một const_iterator. Đó là lý do tại sao mã sẽ không biên dịch.

How do I fix this?

Trong C++ 11, đây không phải là vấn đề, do đó không cần sửa. Đó là bởi vì trong C++ 11, hàm map::erase có chữ ký sau, và do đó chấp nhận một const_iterator.

iterator erase(const_iterator position); 

Nếu bạn không thể sử dụng tiêu chuẩn mới, bạn sẽ phải thay đổi biến của mình thành iterator thay thế.

+0

Cảm ơn bạn. Tôi đã rách tóc của tôi về điều này. – ontherocks

+0

Làm thế nào để bạn vượt qua một trình lặp? Ví dụ mã xin vui lòng? – JackKalish

+0

@JackKalish Er .... 'm.erase (it)'? –

2

Xem những gì các bậc thầy nói:

Scot Meyers trong STL hiệu quả

mục 26. thích iterator để iterator const, reverse_iterator, và const_reverse_iterator. Mặc dù các thùng chứa hỗ trợ bốn loại trình vòng lặp, nhưng một trong các loại đó có các đặc quyền mà những người khác không có. Kiểu đó là iterator, iterator là đặc biệt.

typedef deque<int> IntDeque; //STL container and 
typedef lntDeque::iterator Iter; // iterator types are easier 
typedef lntDeque::const_iterator ConstIter; // to work with if you 
// use some typedefs 
Iter i; 
ConstIter ci; 
… //make i and ci point into 
// the same container 
if (i == ci) ... //compare an iterator 
// and a const_iterator 

Mục 27. Sử dụng khoảng cách và tiến trình để chuyển đổi bộ tách const_iterators thành bộ lặp.

typedef deque<int> IntDeque; //convenience typedefs 
typedef lntDeque::iterator Iter; 
typedef lntDeque::const_iterator ConstIter; 
ConstIter ci; // ci is a const_iterator 
… 
Iter i(ci); // error! no implicit conversion from 
// const_iterator to iterator 
Iter i(const_cast<Iter>(ci)); // still an error! can't cast a 
// const_iterator to an iterator 

Điều gì làm việc là trước và khoảng cách

typedef deque<int> IntDeque; //as before 
typedef IntDeque::iterator Iter; 
typedef IntDeque::const_iterator ConstIter; 
IntDeque d; 
ConstIter ci; 
… // make ci point into d 
Iter i(d.begin()); // initialize i to d.begin() 
Advance(i, distance(i, ci)) //move i up to where ci is 
// (but see below for why this must 
// be tweaked before it will compile) 
Các vấn đề liên quan