在一套非常复杂的题目叙述后,这道题求的是,最多有多少行相同或者完全相反。
只要任意两行在相同的列, 出现不同的数,就可以通过flip这一列来使这两行完全相同。一个例子
1 1 0 1 0
0 0 1 0 1
1 1 1 1 1
0 0 0 0 0
1 1 0 1 0
在这个例子中,0, 1, 4行可以通过翻转2, 4列来完全相同。
那么如何让 [1 1 0 1 0] 与 [0 0 1 0 1] 被认为相同的行呢? 我们可以判断每一行的第一列元素,让他们都是 1 (或者是0), 如果不是 1, 就翻转整个行。 然后判断有多少相同的行,可以将每一行加入hash表,或者通过什么方法来计算hash值。需要注意hash碰撞。
static int x = [] () {ios::sync_with_stdio(false); cin.tie(0); return 0;} ();
class Solution {
public:
int maxEqualRowsAfterFlips(vector<vector<int>>& matrix) {
constexpr int kSeed = 300; // max matrix size
auto boost_hash = [&] (vector<int> &row) {
unsigned int seed = kSeed;
for(auto &i: row) seed ^= i + 0x9e3779b9 + (seed << 6) + (seed >> 2);
return seed;
};
auto rboost_hash = [&] (vector<int> &row) {
unsigned int seed = kSeed;
for(auto &i: row) seed ^= (i^1) + 0x9e3779b9 + (seed << 6) + (seed >> 2);
return seed;
};
unordered_map<unsigned int, int> m;
for (auto &row: matrix)
if (row.front() == 1)
++m[boost_hash(row)];
else
++m[rboost_hash(row)];
int res = 0;
for (auto &[_, num]: m) res = max(res, num);
return res;
}
};