#include <iostream>
#include <memory>
#include <vector>
static const uint64_t SEED = 0xDEADBEEFull;
static const size_t ROWS = 10000;
static const size_t COLS = 10000;
static const uint32_t COLORS_NUM = 3;
uint32_t LCGRand()
{
static uint64_t seed = SEED;
seed = seed * 6364136223846793005 + 1442695040888963407;
return seed >> 32;
}
struct Block {
typedef std::shared_ptr<Block> Ptr;
uint32_t color;
size_t size;
Ptr redir;
};
int main()
{
std::vector<Block::Ptr> up_row(COLS);
size_t max_size = 0;
for (size_t row = 0; row < ROWS; row++) {
Block::Ptr left;
for (size_t col = 0; col < COLS; col++) {
uint32_t color = LCGRand() % COLORS_NUM;
Block::Ptr &up = up_row[col];
while (up && up->redir)
up = up->redir;
Block::Ptr cur;
if (left && (left->color == color)) {
cur = left;
if (up && (up->color == color) && (up != left)) {
left->size += up->size;
up->redir = left;
}
} else if (up && (up->color == color)) {
cur = up;
} else {
cur = std::make_shared<Block>(Block{color, 0, nullptr});
}
max_size = std::max(max_size, ++cur->size);
left = up = cur;
}
}
std::cout << "Max block size: " << max_size << std::endl;
return 0;
}
I2luY2x1ZGUgPGlvc3RyZWFtPgojaW5jbHVkZSA8bWVtb3J5PgojaW5jbHVkZSA8dmVjdG9yPgoKc3RhdGljIGNvbnN0IHVpbnQ2NF90IFNFRUQgPSAweERFQURCRUVGdWxsOwpzdGF0aWMgY29uc3Qgc2l6ZV90IFJPV1MgPSAxMDAwMDsKc3RhdGljIGNvbnN0IHNpemVfdCBDT0xTID0gMTAwMDA7CnN0YXRpYyBjb25zdCB1aW50MzJfdCBDT0xPUlNfTlVNID0gMzsKCnVpbnQzMl90IExDR1JhbmQoKQp7CiAgICBzdGF0aWMgdWludDY0X3Qgc2VlZCA9IFNFRUQ7CiAgICBzZWVkID0gc2VlZCAqIDYzNjQxMzYyMjM4NDY3OTMwMDUgKyAxNDQyNjk1MDQwODg4OTYzNDA3OwogICAgcmV0dXJuIHNlZWQgPj4gMzI7Cn0KCnN0cnVjdCBCbG9jayB7Cgl0eXBlZGVmIHN0ZDo6c2hhcmVkX3B0cjxCbG9jaz4gUHRyOwoJCgl1aW50MzJfdCBjb2xvcjsKCXNpemVfdCBzaXplOwoJUHRyIHJlZGlyOwp9OwoKaW50IG1haW4oKQp7CglzdGQ6OnZlY3RvcjxCbG9jazo6UHRyPiB1cF9yb3coQ09MUyk7CglzaXplX3QgbWF4X3NpemUgPSAwOwoJCiAgICBmb3IgKHNpemVfdCByb3cgPSAwOyByb3cgPCBST1dTOyByb3crKykgewogICAgCUJsb2NrOjpQdHIgbGVmdDsKICAgIAkKICAgIAlmb3IgKHNpemVfdCBjb2wgPSAwOyBjb2wgPCBDT0xTOyBjb2wrKykgewogICAgCQl1aW50MzJfdCBjb2xvciA9IExDR1JhbmQoKSAlIENPTE9SU19OVU07CiAgICAJCQogICAgCQlCbG9jazo6UHRyICZ1cCA9IHVwX3Jvd1tjb2xdOwogICAgCQl3aGlsZSAodXAgJiYgdXAtPnJlZGlyKQogICAgCQkJdXAgPSB1cC0+cmVkaXI7CgogICAgCQlCbG9jazo6UHRyIGN1cjsKICAgIAkJaWYgKGxlZnQgJiYgKGxlZnQtPmNvbG9yID09IGNvbG9yKSkgewogICAgCQkJY3VyID0gbGVmdDsKICAgIAkJCQogICAgCQkJaWYgKHVwICYmICh1cC0+Y29sb3IgPT0gY29sb3IpICYmICh1cCAhPSBsZWZ0KSkgewogICAgCQkJCWxlZnQtPnNpemUgKz0gdXAtPnNpemU7CiAgICAJCQkJdXAtPnJlZGlyID0gbGVmdDsKICAgIAkJCX0KICAgIAkJfSBlbHNlIGlmICh1cCAmJiAodXAtPmNvbG9yID09IGNvbG9yKSkgewogICAgCQkJY3VyID0gdXA7CiAgICAJCX0gZWxzZSB7CiAgICAJCQljdXIgPSBzdGQ6Om1ha2Vfc2hhcmVkPEJsb2NrPihCbG9ja3tjb2xvciwgMCwgbnVsbHB0cn0pOwogICAgCQl9CiAgICAJCQogICAgCQltYXhfc2l6ZSA9IHN0ZDo6bWF4KG1heF9zaXplLCArK2N1ci0+c2l6ZSk7CiAgICAJCWxlZnQgPSB1cCA9IGN1cjsKICAgIAl9CiAgICB9CgkKICAgIHN0ZDo6Y291dCA8PCAiTWF4IGJsb2NrIHNpemU6ICIgPDwgbWF4X3NpemUgPDwgc3RkOjplbmRsOwogICAgcmV0dXJuIDA7Cn0K