Advertisement
Not a member of Pastebin yet?
Sign Up,
it unlocks many cool features!
- #include <iostream>
- #include <string>
- #include <cstring>
- #include <cstdio>
- #include <cinttypes>
- #pragma GCC optimize("O3")
- constexpr int INT_CHAR = 8;
- class Account
- {
- public:
- static constexpr int DATA_SIZE = 4;
- Account()
- {
- memset(data, 0, sizeof(data));
- }
- Account(const uint32_t *data_)
- {
- memcpy(data, data_, sizeof(data));
- }
- Account(const Account &a) :Account(a.data) {}
- Account(const std::string &s);
- explicit operator bool() const;
- std::string to_string() const;
- const uint32_t *cdata() const
- {
- return data;
- }
- friend bool operator<(const Account &a, const Account &b);
- friend bool operator>(const Account &a, const Account &b);
- friend bool operator==(const Account &a, const Account &b);
- friend bool operator!=(const Account &a, const Account &b);
- friend bool operator<=(const Account &a, const Account &b);
- friend bool operator>=(const Account &a, const Account &b);
- friend struct std::hash<Account>;
- private:
- uint32_t data[DATA_SIZE];
- int hex_to_int(char a) const
- {
- constexpr int HEX_A = 10;
- if (a <= '9') {
- return a - '0';
- } else if (a <= 'Z') {
- return HEX_A + a - 'A';
- } else {
- return HEX_A + a - 'a';
- }
- }
- int cmp(const Account &other) const
- {
- for (int i = DATA_SIZE-1; i >= 0; i--) {
- if (data[i] > other.data[i]) {
- return 1;
- } else if (data[i] < other.data[i]) {
- return -1;
- }
- }
- return 0;
- }
- };
- bool operator<(const Account &a, const Account &b)
- {
- return a.cmp(b) < 0;
- }
- bool operator>(const Account &a, const Account &b)
- {
- return a.cmp(b) > 0;
- }
- bool operator==(const Account &a, const Account &b)
- {
- return a.cmp(b) == 0;
- }
- bool operator!=(const Account &a, const Account &b)
- {
- return a.cmp(b) != 0;
- }
- bool operator<=(const Account &a, const Account &b)
- {
- return a.cmp(b) <= 0;
- }
- bool operator>=(const Account &a, const Account &b)
- {
- return a.cmp(b) >= 0;
- }
- Account::Account(const std::string &s)
- {
- constexpr int HEX_START = 2;
- constexpr int HALF_BYTE = 4;
- memset(data, 0, sizeof(data));
- int hex_len = s.length();
- int i = 0;
- int j = hex_len;
- while(i < DATA_SIZE && j >= HEX_START) {
- for (int k = std::max(HEX_START, j - INT_CHAR); k < j; k++) {
- data[i] <<= HALF_BYTE;
- data[i] |= hex_to_int(s[k]);
- }
- i += 1;
- j -= INT_CHAR;
- }
- }
- Account::operator bool() const
- {
- for (int i = 0; i < DATA_SIZE; i++) {
- if (data[i]) {
- return true;
- }
- }
- return false;
- }
- std::string Account::to_string() const
- {
- constexpr int STR_SIZE = 32 + 2 + 1;
- char str[STR_SIZE] = "0x";
- if (!operator bool()) {
- str[1] = 0;
- return str;
- } else {
- int i = DATA_SIZE - 1;
- int j = 0;
- while (i >= 0) {
- sprintf(str+2+INT_CHAR*j, "%08x", data[i]);
- i -= 1;
- j += 1;
- }
- return str;
- }
- }
- namespace std
- {
- template<>
- struct hash<Account>
- {
- size_t operator()(const Account &a) const
- {
- uint32_t res = 0;
- for (int i = 0; i < Account::DATA_SIZE; i++) {
- res ^= a.data[i];
- }
- return res;
- }
- };
- }
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement