如何避免创建空对象?

时间:2019-05-01 19:08:01

标签: c++ function object pointers set

我正在做作业,我有2个函数unionRect和intersectRect.I从文件创建一组第一类Rectangle。我必须返回该oColl的并集和相交矩形。由于对象返回两个0值,因此返回值存在问题。

我试图返回其他东西,但我做不到。

这是来自一流的矩形

Rectangle unionRect(const Rectangle& rec) const {
            int ux1, ux2, uy1, uy2;
            ux1 = min(ix1, rec.ix1);
            uy1 = min(iy1, rec.iy1);
            ux2 = max(ix2, rec.ix2);
            uy2 = max(iy2, rec.iy2);
            Rectangle a(ux1, ux2, uy1, uy2);
            return a;
    }

这是第二类RectangleCollection函数,可以从文件中读取

RectangleCollection(const string& strFileName) {
        ifstream ifile(strFileName.data());
        copy(istream_iterator<Rectangle>(ifile), istream_iterator<Rectangle>(), inserter(oColl,oColl.begin()));
    };

这是我的联合Rect的RectangleCollection类函数

Rectangle calcUnionColl() {
        set<Rectangle>::iterator it;
        Rectangle a;
        for (it = oColl.begin(); it != oColl.end(); ++it) {
         a = unionRect(*it);
        }
        return a;

    }

.txt文件是

5 5 10 10
6 6 12 12

但是当我致电calcUnionColl时,它会返回我

x1:0 x2:6 y1:0 y2:12

我希望输出为x1:5 x2:6 y1:5 y2:12。 预先谢谢你!

2 个答案:

答案 0 :(得分:0)

您并没有将集合中的所有Rectangle合并在一起。您只将每个Rectangle与调用Rectangle的那个calcUnionColl()合并在一起,然后返回仅执行最后一个合并的结果。

请尝试以下类似操作:

class Rectangle {
public:
    ...
    Rectangle unionRect(const Rectangle& rec) const;
    ...
}

Rectangle Rectangle::unionRect(const Rectangle& rec) const {
    int ux1, ux2, uy1, uy2;
    ux1 = std::min(ix1, rec.ix1);
    uy1 = std::min(iy1, rec.iy1);
    ux2 = std::max(ix2, rec.ix2);
    uy2 = std::max(iy2, rec.iy2);
    return Rectangle(ux1, ux2, uy1, uy2);
}

...

class RectangleCollection {
public:
    ...
    Rectangle calcUnionColl() const;
    ...
}

Rectangle RectangleCollection::calcUnionColl() const {
    Rectangle a;
    if (!oColl.empty()) {
        std::set<Rectangle>::iterator it = oColl.begin();
        a = *it++;
        while (it != oColl.end()) {
            a = a.unionRect(*it++);
        }
    }
    return a;
}

答案 1 :(得分:0)

雷米·勒博(Remy Lebeau)的回答有一个小问题。如果calcUnionColl为空,则a将返回默认构造的值a。因此,如果x1:0, x2:0, y1:0, y2:0的默认构造值为calcUnionColl,则如果oColl返回该值,则不可能知道这是否是oColl中值的实际并集, 或者如果 int是空的。

找到多个INT_MIN的最大值时,一个常见的技巧是使用INT_MAX初始化运行最大值。同样,在找到最小值时,我们用a = {x1:INT_MAX, x2:INT_MIN, y1:INT_MAX, y2:INT_MIN}初始化运行最小值。

找到矩形的并集只不过是找到矩形角坐标的最小值/最大值,因此我们可以使用上述技巧。

例如,如果a,则在计算b与任何矩形b.x1 <= a.x1 // a.x1 == INT_MAX b.y1 <= a.y1 // a.y1 == INT_MAX b.x2 >= a.x1 // a.x1 == INT_MIN b.y2 >= a.y2 // a.y2 == INT_MIN 的并集时,我们将得到:

a

因此,在这种情况下,bb的并集将是calcUnionColl()

// I assume the data-type for your rectangle coordinates is `int`. // If you use another datatype, change this accoringly. Rectangle RectangleCollection::calcUnionColl() const { int i_min = std::numeric_limit<int>::min(); // c++ way of getting INT_MIN int i_max = std::numeric_limit<int>::max(); // c++ way of getting INT_MAX set<Rectangle>::iterator it; Rectangle a(i_max, i_min, i_max, i_min); for (it = oColl.begin(); it != oColl.end(); ++it) { a = a.unionRect(*it); } return a; } 中使用它:

oColl

现在,如果calcUnionColl()为空,则x1:INT_MAX, x2:INT_MIN, y1:INT_MAX, y2:INT_MIN将返回x1>x2。自y1>y2 i j +----+ +----+ | 10 | | | +----+ +----+ [p = &j; p is the location of j] i j +----+ +----+ | 10 | | | +----+ +----+ ^ | p [q = malloc(sizeof(int)); q is the location of an unnamed int] i j +----+ +----+ +----+ | 10 | | | | | +----+ +----+ +----+ ^ ^ | | p q [*q = i; replace the value of the int that q points to with i's value] i j +----+ +----+ +----+ | 10 | | | | 10 | +----+ +----+ +----+ ^ ^ | | p q [j = i; replace the value of j with the value of i] i j +----+ +----+ +----+ | 10 | | 10 | | 10 | +----+ +----+ +----+ ^ ^ | | p q [q = p; replace the value of q with the value of p, i.e. they are both &j] i j +----+ +----+ +----+ | 10 | | 10 | | 10 | +----+ +----+ +----+ ^ ^ | | p q [*q = 5; replace the value of the int that q points to with 5] i j +----+ +----+ +----+ | 10 | | 5 | | 10 | +----+ +----+ +----+ ^ ^ | | p q 起,这对于矩形来说应该是无效的值,并且应该易于测试。

有时候,您甚至不必测试它,因为它通常是一个“有意义的”无效值,可以进行进一步的计算。

相关问题