将较小的向量与较大的向量进行比较,以检查较小的向量的末尾是否不同

时间:2018-12-20 08:10:19

标签: c++ c++11

我们有两个大小取决于运行时间的向量,需要检查它们是否相等-仅在较小大小向量结束后才可以使用不同的元素。我使用了std :: equal,但是问题是我需要首先找到哪个矢量的大小较小,这会导致额外的代码行:

!!

用于比较两个向量或仅在较小向量的末尾不同的代码可以改进吗?

3 个答案:

答案 0 :(得分:23)

从C ++ 14开始,您可以使用std::mismatch并检查每个范围末尾返回的一对迭代器:

auto it = std::mismatch(a.begin(), a.end(), a1.begin(), a1.end());
if (it.first == a.end() || it.second == a1.end()) {
    // Equality
}

您还将了解元素在哪里开始不同,如果元素之间没有差异,则在那个时候较大的矢量会更大(您不想比较的子范围的开始)。

答案 1 :(得分:8)

如果您事先计算出较小的尺寸,则只需调用一次std::equal。我将重构这样的代码:

#include <vector>
#include <iostream>
#include <algorithm>

int main()
{
    std::vector<int> a(1000, 3);
    std::vector<int> a1(100, 3);

    if (std::equal(a1.begin(), a1.begin() + std::min(a.size(), a1.size()), a.begin())) 
    {
        std::cout << "Same" << std::endl;
    }
    return 0;
}

如果您需要保留有关哪个向量更大的第二个信息,则可以这样实现,例如:

std::cout << "Same " << ((a.size() == a1.size())? "a = a1" : ((a.size() > a1.size())? "a gt a1" : "a1 gt a")) << std::endl;

答案 2 :(得分:0)

这里是纯C ++ 11解决方案,该解决方案适用于任何顺序容器(例如std::vectorstd::liststd::deque)。它使用自定义返回类型,因为您在原始代码段中显示的比较类型包含的信息比简单的布尔值可以包含的信息更多。

enum class CombinedCompareResult {
   NotEqual, EqualAndFirstLarger, EqualAndSecondLarger, EqualIncludingSize
};

template <class Rng1, class Rng2>
CombinedCompareResult combinedCompare(const Rng1& rng1, const Rng2& rng2)
{
   using std::begin;

   const auto elementsToCompare = std::min(rng1.size(), rng2.size());

   if (!std::equal(begin(rng1), std::next(begin(rng1), elementsToCompare), begin(rng2)))
      return CombinedCompareResult::NotEqual;
   else if (rng1.size() == rng2.size())
      return CombinedCompareResult::EqualIncludingSize;
   else if (rng1.size() > rng2.size())
      return CombinedCompareResult::EqualAndFirstLarger;
   else
      return CombinedCompareResult::EqualAndSecondLarger;
}

这可以像以下一样使用,并且应导致与问题代码相同的行为。

const auto cmp = combinedCompare(lst, a);

if (cmp == CombinedCompareResult::EqualIncludingSize)
    std::cout << "Same a = a1" << std::endl;
else if (cmp == CombinedCompareResult::EqualAndFirstLarger)
    std::cout << "Same a gt a1" << std::endl;
else if (cmp == CombinedCompareResult::EqualAndSecondLarger)
    std::cout << "Same a1 gt a" << std::endl;