#include <bits/stdc++.h>
#include <ext/pb_ds/assoc_container.hpp>
#include <ext/pb_ds/tree_policy.hpp>
using namespace std;
using namespace __gnu_pbds;
typedef pair<int, int> pii;
typedef tree<int, null_type, less<int>, rb_tree_tag, tree_order_statistics_node_update> ordered_map;
typedef cc_hash_table<int, int, hash<int>> ht;
// typedef cc_hash_table<
// int, int, hash<int>, equal_to<int>, direct_mask_range_hashing<int>,
// hash_standard_resize_policy<hash_exponential_size_policy<>, hash_load_check_resize_trigger<true>, true>>
// ht;
bool eraseVals = false;
void benchmarkPolicy(string msg, vector<pii> &vals, int NUM_ITERS) {
clock_t begin = clock();
ht test;
for (int t = 0; t < NUM_ITERS; t++) {
for (auto i : vals) {
test[i.first] = test[i.first] + i.second * t;
}
}
cout << msg << ": " << string(60 - msg.size(), ' ') << "\t" << (double)(clock() - begin) / CLOCKS_PER_SEC << endl;
}
void benchmarkStl(string msg, vector<pii> &vals, int NUM_ITERS) {
clock_t begin = clock();
unordered_map<int, int> test;
for (int t = 0; t < NUM_ITERS; t++) {
for (auto i : vals) {
test[i.first] = test[i.first] + i.second * t;
}
}
cout << msg << ": " << string(60 - msg.size(), ' ') << "\t" << (double)(clock() - begin) / CLOCKS_PER_SEC << endl;
}
void benchmark(string msg, vector<pii> vals, int NUM_ITERS) {
benchmarkStl("unordered map " + msg, vals, NUM_ITERS);
benchmarkPolicy("policy hash table " + msg, vals, NUM_ITERS);
cout << endl;
}
vector<pii> generateVec(int max_val, bool shuffled) {
vector<int> k(max_val), v(max_val);
vector<pii> vals;
iota(k.begin(), k.end(), 0);
iota(v.begin(), v.end(), 0);
if (shuffled) {
random_shuffle(k.begin(), k.end());
random_shuffle(v.begin(), v.end());
}
for (int i = 0; i < max_val; i++) {
vals.push_back({k[i], v[i]});
}
return vals;
}
int main() {
ios::sync_with_stdio(0);
cin.tie(0);
benchmark("linear insertion", generateVec(1e7, false), 1);
benchmark("linear read/write", generateVec(1e5, false), 1000);
benchmark("random insertion", generateVec(1e7, true), 1);
benchmark("random read/write", generateVec(1e5, true), 1000);
}
I2luY2x1ZGUgPGJpdHMvc3RkYysrLmg+CiNpbmNsdWRlIDxleHQvcGJfZHMvYXNzb2NfY29udGFpbmVyLmhwcD4KI2luY2x1ZGUgPGV4dC9wYl9kcy90cmVlX3BvbGljeS5ocHA+Cgp1c2luZyBuYW1lc3BhY2Ugc3RkOwoKdXNpbmcgbmFtZXNwYWNlIF9fZ251X3BiZHM7CnR5cGVkZWYgcGFpcjxpbnQsIGludD4gcGlpOwp0eXBlZGVmIHRyZWU8aW50LCBudWxsX3R5cGUsIGxlc3M8aW50PiwgcmJfdHJlZV90YWcsIHRyZWVfb3JkZXJfc3RhdGlzdGljc19ub2RlX3VwZGF0ZT4gb3JkZXJlZF9tYXA7CnR5cGVkZWYgY2NfaGFzaF90YWJsZTxpbnQsIGludCwgaGFzaDxpbnQ+PiBodDsKLy8gdHlwZWRlZiBjY19oYXNoX3RhYmxlPAovLyAgICAgaW50LCBpbnQsIGhhc2g8aW50PiwgZXF1YWxfdG88aW50PiwgZGlyZWN0X21hc2tfcmFuZ2VfaGFzaGluZzxpbnQ+LAovLyAgICAgaGFzaF9zdGFuZGFyZF9yZXNpemVfcG9saWN5PGhhc2hfZXhwb25lbnRpYWxfc2l6ZV9wb2xpY3k8PiwgaGFzaF9sb2FkX2NoZWNrX3Jlc2l6ZV90cmlnZ2VyPHRydWU+LCB0cnVlPj4KLy8gICAgIGh0OwoKYm9vbCBlcmFzZVZhbHMgPSBmYWxzZTsKdm9pZCBiZW5jaG1hcmtQb2xpY3koc3RyaW5nIG1zZywgdmVjdG9yPHBpaT4gJnZhbHMsIGludCBOVU1fSVRFUlMpIHsKICAgIGNsb2NrX3QgYmVnaW4gPSBjbG9jaygpOwogICAgaHQgdGVzdDsKICAgIGZvciAoaW50IHQgPSAwOyB0IDwgTlVNX0lURVJTOyB0KyspIHsKICAgICAgICBmb3IgKGF1dG8gaSA6IHZhbHMpIHsKICAgICAgICAgICAgdGVzdFtpLmZpcnN0XSA9IHRlc3RbaS5maXJzdF0gKyBpLnNlY29uZCAqIHQ7CiAgICAgICAgfQogICAgfQogICAgY291dCA8PCBtc2cgPDwgIjogIiA8PCBzdHJpbmcoNjAgLSBtc2cuc2l6ZSgpLCAnICcpIDw8ICJcdCIgPDwgKGRvdWJsZSkoY2xvY2soKSAtIGJlZ2luKSAvIENMT0NLU19QRVJfU0VDIDw8IGVuZGw7Cn0KCnZvaWQgYmVuY2htYXJrU3RsKHN0cmluZyBtc2csIHZlY3RvcjxwaWk+ICZ2YWxzLCBpbnQgTlVNX0lURVJTKSB7CiAgICBjbG9ja190IGJlZ2luID0gY2xvY2soKTsKICAgIHVub3JkZXJlZF9tYXA8aW50LCBpbnQ+IHRlc3Q7CiAgICBmb3IgKGludCB0ID0gMDsgdCA8IE5VTV9JVEVSUzsgdCsrKSB7CiAgICAgICAgZm9yIChhdXRvIGkgOiB2YWxzKSB7CiAgICAgICAgICAgIHRlc3RbaS5maXJzdF0gPSB0ZXN0W2kuZmlyc3RdICsgaS5zZWNvbmQgKiB0OwogICAgICAgIH0KICAgIH0KICAgIGNvdXQgPDwgbXNnIDw8ICI6ICIgPDwgc3RyaW5nKDYwIC0gbXNnLnNpemUoKSwgJyAnKSA8PCAiXHQiIDw8IChkb3VibGUpKGNsb2NrKCkgLSBiZWdpbikgLyBDTE9DS1NfUEVSX1NFQyA8PCBlbmRsOwp9Cgp2b2lkIGJlbmNobWFyayhzdHJpbmcgbXNnLCB2ZWN0b3I8cGlpPiB2YWxzLCBpbnQgTlVNX0lURVJTKSB7CiAgICBiZW5jaG1hcmtTdGwoInVub3JkZXJlZCBtYXAgIiArIG1zZywgdmFscywgTlVNX0lURVJTKTsKICAgIGJlbmNobWFya1BvbGljeSgicG9saWN5IGhhc2ggdGFibGUgIiArIG1zZywgdmFscywgTlVNX0lURVJTKTsKICAgIGNvdXQgPDwgZW5kbDsKfQoKdmVjdG9yPHBpaT4gZ2VuZXJhdGVWZWMoaW50IG1heF92YWwsIGJvb2wgc2h1ZmZsZWQpIHsKICAgIHZlY3RvcjxpbnQ+IGsobWF4X3ZhbCksIHYobWF4X3ZhbCk7CiAgICB2ZWN0b3I8cGlpPiB2YWxzOwogICAgaW90YShrLmJlZ2luKCksIGsuZW5kKCksIDApOwogICAgaW90YSh2LmJlZ2luKCksIHYuZW5kKCksIDApOwogICAgaWYgKHNodWZmbGVkKSB7CiAgICAgICAgcmFuZG9tX3NodWZmbGUoay5iZWdpbigpLCBrLmVuZCgpKTsKICAgICAgICByYW5kb21fc2h1ZmZsZSh2LmJlZ2luKCksIHYuZW5kKCkpOwogICAgfQogICAgZm9yIChpbnQgaSA9IDA7IGkgPCBtYXhfdmFsOyBpKyspIHsKICAgICAgICB2YWxzLnB1c2hfYmFjayh7a1tpXSwgdltpXX0pOwogICAgfQogICAgcmV0dXJuIHZhbHM7Cn0KaW50IG1haW4oKSB7CiAgICBpb3M6OnN5bmNfd2l0aF9zdGRpbygwKTsKICAgIGNpbi50aWUoMCk7CiAgICBiZW5jaG1hcmsoImxpbmVhciBpbnNlcnRpb24iLCBnZW5lcmF0ZVZlYygxZTcsIGZhbHNlKSwgMSk7CiAgICBiZW5jaG1hcmsoImxpbmVhciByZWFkL3dyaXRlIiwgZ2VuZXJhdGVWZWMoMWU1LCBmYWxzZSksIDEwMDApOwogICAgYmVuY2htYXJrKCJyYW5kb20gaW5zZXJ0aW9uIiwgZ2VuZXJhdGVWZWMoMWU3LCB0cnVlKSwgMSk7CiAgICBiZW5jaG1hcmsoInJhbmRvbSByZWFkL3dyaXRlIiwgZ2VuZXJhdGVWZWMoMWU1LCB0cnVlKSwgMTAwMCk7Cn0=