Valmir - 4 months ago 10

C++ Question

I need to check if two given sequences are equal, but if I find a mismatched element I need to check in a 3rd sequence (same size of the other two) if that can be ignored.

I know that I can write a simple algorithm to solve that, but I would like to know if there is any C++-like style to solving this, using a std algorithm.

Example:

`A = [1, 2, 3, 4, 5, 6]`

B = [1, 2, 3, A, 5, 6]

M = [true, true, true, false, true, true]

N = [true, true, true, true, true, true]

bool equal1 = the_equal(begin_A, end_A, begin_B, begin_M); // Should return true, even if '4' is different from 'A' since in the same position of the found mismatch, in the M sequence, we have a false that indicates that position should be ignored.

bool equal2 = the_equal(begin_A, end_A, begin_B, begin_N); // Should return false, since '4' is different from 'A' and we have a true in sequence N for that position.

That could be solved by something like:

`template<I1, I2, I3> // iterators`

bool the_equal(I1 first1, I1 last1, I2 first2, I3 first3) {

while (first1 != last1) {

if (*first1 != *first2 && *first3 != false)

return false;

++first1; ++first2; ++first3;

}

return true;

}

Edit: I forgot to say that I need to solve this in c++98 due toolchain limitations :(

Answer

You may create a (mutable) functor:

```
template <typename IT>
struct CmpWithMask
{
CmpWithMask(IT it) : it(it) {}
template <typename LHS, typename RHS>
bool operator () (const LHS& lhs, const RHS& rhs) {
return !*it++ || lhs == rhs;
}
IT it;
};
template <typename IT>
CmpWithMask<IT> MakeCmpWithMask(IT it) { return CmpWithMask<IT>{it}; }
```

And then, use `std::equal`

:

```
std::cout << std::equal(A.begin(), A.end(),
B.begin(),
MakeCmpWithMask(M.begin())) << std::endl;
std::cout << std::equal(A.begin(), A.end(),
B.begin(),
MakeCmpWithMask(N.begin())) << std::endl;
```