c++ - 容器类内部的类迭代器

标签 c++

我需要构建一个内部类迭代器来使用容器类 FigureOfCircles

#define T Circle
    class FigureOfCircles {
private:
    Circle* c;
    int size;
public:
    class Iterator {
    protected:
        T* t;
    public:
        explicit Iterator (T* t1 = 0) : t(t1) { }
        Iterator (const Iterator& x) : t(x.t)  {}
        T& operator*() const { return *t; }
        T* operator->() const { return t; }

        Circle& operator[](const std::size_t& n) { return t[n]; }
        Iterator& operator++() { ++t; return *this; }
        Iterator operator++(int) { return Iterator(t++); }

        Iterator& operator--() { --t; return *this; }
        Iterator operator--(int) { return Iterator(t--); }

        Iterator operator- (int n) { return Iterator(t - n); }
        Iterator operator+ (int n) { return Iterator(t - n); }

        Iterator& operator-= (int n) { t -= n; return *this; }
        Iterator& operator+= (int n) { t += n; return *this; }

        bool operator== (const Iterator& x) const { return t == x.t; }
        bool operator!= (const Iterator& x) const { return t != x.t; }
        bool operator<= (const Iterator& x) const { return t <= x.t; }
        bool operator> (const Iterator& x) const { return t > x.t; }
        bool operator>= (const Iterator& x) const { return t >= x.t; }
        bool operator< (const Iterator& x) const { return t < x.t; }
        friend int operator- (const Iterator& x, const Iterator& y) { return x.t - y.t; }

        Iterator& operator= (const Iterator& x) {
            if (t == x.t) exit(-6);
            t = x.t;
            return *this;
        }
    };

    FigureOfCircles (int sz) : size(sz) {
        c = new T[size];
        for (Iterator i = begin(); i != end(); ++i) *i = input();
    }
    FigureOfCircles(const FigureOfCircles& f) {
        size = f.size;
        c = new T[size];
        for (Iterator i = begin(); i != end(); ++i) *i = f.c[i - begin()];
    }
    ~FigureOfCircles() { if (c) delete[] c; }

    Circle input() {
        int size = 1;
        Point* arr = new Point[size];
        float r, x1, y1;
        cout << endl << "Введiть к-сть точок, радiус i координати центру: ";
        cin >> size >> r >> x1 >> y1;
        for (int i = 0; i < size; i++) {
            Point tmp;
            cin >> tmp;
            if (tmp.GetX() == x1 && tmp.GetY() == y1) exit(-7);
            if (pow(tmp.GetX() - x1, 2) + pow(tmp.GetY() - y1, 2) != r * r) exit(-8);
            arr[i] = tmp;
        }
        return Circle(size, r, arr, x1, y1);        
    }

    Iterator begin() { return Iterator(c); }
    Iterator end() { return Iterator(c+size); }
};

但是我不明白 T 应该是什么类型才能使用迭代器对象?如果是int,那么

Iterator begin() { return Iterator(c); }
Iterator end() { return Iterator(c+size); }

Note:

FigureOfCircles (int sz) : size(sz) {
    c = new T[size];
    for (int i = 0; i < size; i++)
        c[i].input();
    for (Iterator i = begin(); i != end(); ++i) {
        *i = T(i-begin());
    }
}

...

 int main () {
    //...
    FigureOfCircles f(2);
    FigureOfCircles::Iterator i;
    for (i = f.begin(); i != f.end(); i++) cout << *i << endl;
    }

最佳答案

你有一个 Circle 的数组s,指向 c .迭代器应该指向这个数组的元素。最简单的解决方案是使用普通指针。即 T在你的迭代器中应该只是 Circle .

如果你想使用int (它应该是 std::ptrdiff_t ),您的迭代器还应该保留指向第一个元素的指针。在这个特定示例中,我看不到这样做的理由。

operator-应该返回指针之间的差异,std::ptrdiff_t , 不是 Circle :

friend std::ptrdiff_t operator-(Iterator x, Iterator y) { 
    return x.t - y.t;
}

Iterator按值(value)。它只是一个单独的指针,您不需要通过 const-ref 获取它(有效地获取指向指针的指针)。

一旦有了迭代器,就可以使用标准库算法来制作拷贝:而不是

for (Iterator i = begin(); i != end(); ++i) *i = f.c[i - begin()];

你可以写

std::copy(f.begin(), f.end(), begin());

我建议你使用 std::vector<Circle>而不是 Circle* .然后你就可以借用它的迭代器:

class FigureOfCircles {
private:
    std::vector<Circle> c;
public:
    std::vector<Circle>::iterator begin() {
        c.begin();
    }

    std::vector<Circle>::iterator end() {
        c.end();
    }
};

这也将使您免于编写复制构造函数和析构函数。

关于c++ - 容器类内部的类迭代器,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/59128019/

相关文章:

c++ - 无法在初始化列表中捕获

c++ - CalcOpticalFlowLK 相机运动 C++

c++ - 如何声明指向返回函数指针的函数的指针

c++ - 由于在 C++ 中有两种定义转换的方法,当同一个转换有两种可能性时,它们如何交互?

javascript - 设计跨平台多内容类型文件格式的最佳方式?

c++ - 如何防止箭头键改变 UI 状态?

c++ - Qt 在串口上发送完整的字节

针对缓冲区溢出、格式字符串错误和整数溢出的 C++ 安全框架

c++ - 实现 TCP 应用程序内置 shell 的简单方法

c++ - C++ 中 char 数组末尾的空终止符