繁体   English   中英

C ++ STL二进制搜索(lower_bound,upper_bound)

[英]C++ STL Binary Search (lower_bound, upper_bound)

我已经实现了这样的二进制搜索:

typedef std::vector<Cell>::iterator CellVectorIterator;

typedef struct _Point {
    char x,y;
} CoordinatePoint;

typedef struct _Cell {
    ...
    CoordinatePoint coordinates;
} Cell;

struct CellEqualityByCoordinates
{
    bool
    operator()(const Cell& cell1, const Cell& cell2) const
    { return cell1.coordinates.x == cell2.coordinates.x && cell1.coordinates.y == cell2.coordinates.y; }
};

CellVectorIterator FindCellByCoordinates (CellVectorIterator first, CellVectorIterator last, const Cell &val)
{
    return std::upper_bound(first, last, val, CellEqualityByCoordinates());
}

但是,它并不总能找到价值。

怎么了

您的比较功能不适用于二进制搜索。 它不应该确定相等性,它应该确定顺序关系。 具体来说,如果第一个参数在排序范围内肯定要排在第二个参数之前,则应返回true。 如果参数应视为相等,或者第二个参数在第一个参数之前,则应返回false。 您的范围也需要按照相同的条件进行排序,以便二进制搜索正常工作。

可能起作用的示例函数:

bool operator()(const Cell& cell1, const Cell& cell2) const 
{
    if (cell1.coordinates.x < cell2.coordinates.x) return true;
    if (cell2.coordinates.x < cell1.coordinates.x) return false;
    return cell1.coordinates.y < cell2.coordinates.y;
}

在短路布尔值评估中加倍作为教训的类似示例将是:

bool operator()(const Cell& cell1, const Cell& cell2) const 
{
    return (cell1.coordinates.x < cell2.coordinates.x) ||
        (!(cell2.coordinates.x < cell1.coordinates.x) &&
          cell1.coordinates.y < cell2.coordinates.y);
}

两者都具有称为严格弱序的属性。 在标准库集合和搜索算法中经常需要进行各种排序和/或搜索。

另一个示例利用std::pair ,该对象已经具有适当的std::less重载,可以执行上述操作,因此使此操作复杂度大大降低:

bool operator()(const Cell& cell1, const Cell& cell2) const
{
    return std::make_pair(cell1.coordinates.x, cell1.coordinates.y) <
           std::make_pair(cell2.coordinates.x, cell2.coordinates.y);
}

可通过std::tie为元组提供类似的算法。

当然,所有这些都假定您首先具有一个实际的有序序列,并由相同的比较逻辑进行排序。 (我们只能假设它是真实的,因为没有发布任何此类证据)。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM