QOJ.ac

QOJ

IDProblemSubmitterResultTimeMemoryLanguageFile sizeSubmit timeJudge time
#762633#2519. Number with BachelorsSanguineChameleon#AC ✓23ms3624kbC++203.9kb2024-11-19 15:56:172024-11-19 15:56:18

Judging History

你现在查看的是最新测评结果

  • [2024-11-19 15:56:18]
  • 评测
  • 测评结果:AC
  • 用时:23ms
  • 内存:3624kb
  • [2024-11-19 15:56:17]
  • 提交

answer

#include <bits/stdc++.h>
using namespace std;

void justDoIt();

int main() {
    ios_base::sync_with_stdio(false);
    cin.tie(nullptr);
    justDoIt();
    return 0;
}

typedef unsigned long long ull;

int charToHex(char c) {
    if ('0' <= c && c <= '9') {
        return c - '0';
    }
    else {
        return 10 + (c - 'a');
    }
}

char hexToChar(int d) {
    if (0 <= d && d <= 9) {
        return (char)('0' + d);
    }
    else {
        return (char)('a' + (d - 10));
    }
}

ull read(char base) {
    if (base == 10) {
        ull res;
        cin >> res;
        return res;
    }
    else {
        ull res = 0;
        string s;
        cin >> s;
        for (auto c: s) {
            res = res * base + charToHex(c);
        }
        return res;
    }
}

void print(int base, ull res) {
    if (res == -1ULL) {
        cout << '-' << '\n';
        return;
    }
    if (base == 10) {
        cout << res << '\n';
        return;
    }
    else {
        string s = "";
        while (res) {
            s += hexToChar(res % base);
            res /= base;
        }
        if (s.empty()) {
            s = "0";
        }
        reverse(s.begin(), s.end());
        cout << s << '\n';
        return;
    }
}

ull calc0(int base, ull r) {
    if (r == 0) {
        return 1;
    }
    if (r != -1ull) {
        r++;
    }
    vector<int> digits;
    ull cur = r;
    while (cur) {
        digits.push_back(cur % base);
        cur /= base;
    }
    reverse(digits.begin(), digits.end());
    int len = digits.size();
    ull res = 1;
    for (int i = 1; i < len; i++) {
        ull ways = base - 1;
        for (int j = base - 1; j >= base - i + 1; j--) {
            ways *= j;
        }
        res += ways;
    }
    vector<bool> flag(base);
    for (int i = 0; i < len; i++) {
        ull ways = 1;
        int rem = base - (i + 1);
        int suf = len - (i + 1);
        for (int k = rem; k >= rem - suf + 1; k--) {
            ways *= k;
        }
        for (int j = (i == 0 ? 1 : 0); j < digits[i]; j++) {
            if (!flag[j]) {
                res += ways;
            }
        }
        if (flag[digits[i]]) {
            break;
        }
        flag[digits[i]] = true;
    }
    return res;
}

ull calc1(int base, ull pos) {
    if (pos == 1) {
        return 0;
    }
    pos--;
    ull ways = base - 1;
    int len = 1;
    for (; len <= base; len++) {
        if (pos > ways) {
            pos -= ways;
        }
        else {
            break;
        }
        ways *= base - len;
    }
    if (len > base) {
        return -1;
    }
    pos--;
    vector<ull> suf(len + 1);
    for (int i = 0; i < len; i++) {
        suf[i] = base - i;
    }
    suf[len] = 1;
    for (int i = len - 1; i >= 0; i--) {
        suf[i] *= suf[i + 1];
    }
    vector<int> order(len);
    for (int i = 0; i < len; i++) {
        order[i] = pos / suf[i + 1];
        pos %= suf[i + 1];
    }
    vector<bool> flag(base);
    ull res = 0;
    for (int i = 0; i < len; i++) {
        int cnt = order[i];
        for (int d = (i == 0 ? 1 : 0); d < base; d++) {
            if (!flag[d]) {
                if (cnt == 0) {
                    res = res * base + d;
                    flag[d] = true;
                    break;
                }
                cnt--;
            }
        }
    }
    return res;
}

void test() {
    char b;
    cin >> b;
    int base = (b == 'd' ? 10 : 16);
    int type;
    cin >> type;
    if (type == 0) {
        ull l = read(base);
        ull r = read(base);
        ull res = calc0(base, r) - (l == 0 ? 0 : calc0(base, l - 1));
        print(base, res);
    }
    else {
        ull pos = read(base);
        ull res = calc1(base, pos);
        print(base, res);
    }
}

void justDoIt() {
    int t;
    cin >> t;
    for (int i = 0; i < t; i++) {
        test();
    }
}

Details

Tip: Click on the bar to expand more detailed information

Test #1:

score: 100
Accepted
time: 0ms
memory: 3624kb

input:

6
d 0 10 20
h 0 10 1f
d 1 10
h 1 f
d 1 1000000000
h 1 ffffffffffffffff

output:

10
f
9
e
-
-

result:

ok 6 lines

Test #2:

score: 0
Accepted
time: 23ms
memory: 3576kb

input:

50000
h 1 147a
d 0 25 71
d 1 3587
d 0 26922 51887
d 1 711
d 0 3 5
h 0 7bf2defab442a0b1 f299a4cf1d4d9bed
d 0 6961 91018
d 1 4
d 1 876
h 1 12cc5d3370f99120
d 1 161315
h 0 25f 6959
d 0 467 516
d 1 298
h 1 70260cdc2da73281
h 1 928e17d65d764ca2
h 1 c8ec8a7b67605e51
d 1 91697
d 0 4941925161850941148 89850...

output:

1b36
43
6587
7710
953
3
8daab378500
26054
3
1356
-
946307
4681
40
387
-
-
-
491850
0
1
29
-
4605298
1
1
-
15b4
175f
9b944134000
124b7
6279
9
6257
-
39be22a900
5c636b59300
146ce
2a55
-
0
-
7
d
6
2041
-
1c94afe7300
0
5
9149
16540973
1389
125
0
-
3bc31189480
424
66800
7
-
-
1e6
0
0
48b6
9
-
2b0
5019
14...

result:

ok 50000 lines