QOJ.ac

QOJ

ID题目提交者结果用时内存语言文件大小提交时间测评时间
#536080#9156. 百万富翁Zanite100 ✓3002ms102164kbC++2010.9kb2024-08-28 18:18:422024-08-28 18:18:43

Judging History

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

  • [2024-08-28 18:18:43]
  • 评测
  • 测评结果:100
  • 用时:3002ms
  • 内存:102164kb
  • [2024-08-28 18:18:42]
  • 提交

answer

// こんな僕等がお互い蹴落として
// まで掴んだ物は何ですか
// 僕は 僕を愛してあげたい
// 
// こんなことなら生まれてこなけりゃって
// 全部嫌になってくけれど
// 絶えず 脈打つこれは何だろう
// 
// 何だろう...

#include <bits/stdc++.h>
#include <ext/pb_ds/assoc_container.hpp>
#include <ext/pb_ds/tree_policy.hpp>

#include "richest.h"

// Pragmas
// #pragma GCC optimize("Ofast")
// #pragma GCC optimize("unroll-loops")
// #pragma GCC target("sse,sse2,sse3,ssse3,sse4,popcnt,abm,mmx,avx,tune=native")

// Namespaces
using namespace std;
using namespace __gnu_pbds;

// Data types
using si  = short int;
using ll  = long long;
using ull = unsigned long long;
using lll = __int128;
using ld  = long double;

// Pairs
using pii  = pair<int, int>;
using psi  = pair<si, si>;
using pll  = pair<ll, ll>;
using plll = pair<lll, lll>;
using pld  = pair<ld, ld>;
#define fi first
#define se second

// PBDS
template<typename Z>
using ordered_set = tree<Z, null_type, less<Z>, rb_tree_tag, tree_order_statistics_node_update>;

// Various outputs and debug
template<typename Z, typename = void> struct is_iterable : false_type {};
template<typename Z> struct is_iterable<Z, void_t<decltype(begin(declval<Z>())),decltype(end(declval<Z>()))>> : true_type {};
template<typename Z> typename enable_if<is_iterable<Z>::value&&!is_same<Z, string>::value,ostream&>::type operator<<(ostream &os, const Z &v);

template<typename Y, typename Z> ostream& operator<<(ostream &os, const pair<Y, Z> &p) {
    return os << "(" << p.fi << ", " << p.se << ")";
}
template<class TupType, size_t... I> void printTuple(ostream& os, const TupType& _tup, index_sequence<I...>) {
    os << "(";
    (..., (os << (I == 0? "" : ", ") << get<I>(_tup)));
    os << ")";
}
template<class... Z> ostream& operator<<(ostream& os, const tuple<Z...>& _tup) {
    printTuple(os, _tup, make_index_sequence<sizeof...(Z)>());
    return os;
}
template<typename Z> typename enable_if<is_iterable<Z>::value&&!is_same<Z, string>::value,ostream&>::type operator<<(ostream &os, const Z &v) {
    os << "["; 
    for (auto it = v.begin(); it != v.end();) { os << *it; if (++it != v.end()) os << ", "; }
    return os << "]";
}

#define debug(...)    logger(cout, #__VA_ARGS__, __VA_ARGS__)
#define debugV(v, x)  vlogger(cout, #v, x, v[x]);
#define rrebug(...)   logger(cerr, #__VA_ARGS__, __VA_ARGS__)
#define rrebugV(v, x) vlogger(cerr, #v, x, v[x]);
template <typename... Args>
void logger(ostream& os, string vars, Args &&...values) {
    os << vars << " = "; string delim = "";
    (..., (os << delim << values, delim = ", "));
    os << "\n";
}
template<class Y, class Z>
void vlogger(ostream& os, string var, Y idx, Z val) {
    os << var << "[" << idx << "] = " << val << "\n";
}

// Various macros
#define All(x)            x.begin(), x.end()
#define Sort(x)           sort(All(x))
#define Reverse(x)        reverse(All(x))
#define Uniqueify(x)      Sort(x); x.erase(unique(All(x)), x.end())
#define RandomSeed        chrono::steady_clock::now().time_since_epoch().count()
#define MultipleTestcases int _tc; cin >> _tc; for (int _cur_tc = 1; _cur_tc <= _tc; _cur_tc++)

// Chmin & chmax
template<typename Z> bool chmin(Z &a, Z b) { return (b < a) ? a = b, true : false; }
template<typename Z> bool chmax(Z &a, Z b) { return (b > a) ? a = b, true : false; }
 
// Modular arithmetic
template<int MOD>
class ModInt {
  public:
    int v;
    ModInt() : v(0) {}
    ModInt(long long _v) {
        v = int((-MOD < _v && _v < MOD) ? (_v) : (_v % MOD));
        if (v < 0) v += MOD;
    }
 
    friend bool operator==(const ModInt &a, const ModInt &b) { return a.v == b.v; }
    friend bool operator!=(const ModInt &a, const ModInt &b) { return a.v != b.v; }
    friend bool operator< (const ModInt &a, const ModInt &b) { return a.v <  b.v; }
    friend bool operator<=(const ModInt &a, const ModInt &b) { return a.v <= b.v; }
    friend bool operator> (const ModInt &a, const ModInt &b) { return a.v >  b.v; }
    friend bool operator>=(const ModInt &a, const ModInt &b) { return a.v >= b.v; }
 
    ModInt &operator+=(const ModInt &a) { if ((v += a.v) >= MOD) v -= MOD; return *this; }
    ModInt &operator-=(const ModInt &a) { if ((v -= a.v) < 0) v += MOD; return *this; }
    ModInt &operator*=(const ModInt &a) { v = 1ll * v * a.v % MOD; return *this; }
    ModInt &operator/=(const ModInt &a) { return (*this) *= inverse(a); }
 
    friend ModInt pow(ModInt a, long long x) {
        ModInt res = 1;
        for (; x; x /= 2, a *= a) if (x & 1) res *= a;
        return res;
    }
    friend ModInt inverse(ModInt a) { return pow(a, MOD - 2); }
 
    ModInt operator+ () const { return ModInt( v); }
    ModInt operator- () const { return ModInt(-v); }
    ModInt operator++() const { return *this += 1; }
    ModInt operator--() const { return *this -= 1; }
 
    friend ModInt operator+(ModInt a, const ModInt &b) { return a += b; }
    friend ModInt operator-(ModInt a, const ModInt &b) { return a -= b; }
    friend ModInt operator*(ModInt a, const ModInt &b) { return a *= b; }
    friend ModInt operator/(ModInt a, const ModInt &b) { return a /= b; }
 
    friend istream &operator>>(istream &is, ModInt &v) { return is >> v.v; }
    friend ostream &operator<<(ostream &os, const ModInt &v) { return os << v.v; }
};
const int ModA = 998244353;
const int ModC = 1e9 + 7;
using MintA    = ModInt<ModA>;
using MintC    = ModInt<ModC>;

// Other constants
const ll INF  = 1e18;
const ll iINF = 1e9;
const ld EPS  = 1e-9;
const ld iEPS = 1e-6;

namespace Solver1 {

const int N = 1'000;

int solve() {
    vector<int> Q1, Q2;
    for (int i = 0; i < N; i++) {
        for (int j = i+1; j < N; j++) {
            Q1.push_back(i); Q2.push_back(j);
        }
    }

    vector<int> ans = ask(Q1, Q2);

    vector results(N, vector(N, false));
    for (int t = 0, i = 0; i < N; i++) {
        results[i][i] = true;
        for (int j = i+1; j < N; j++) {
            results[i][j] = (ans[t++] == i);
            results[j][i] = 1 ^ results[i][j];
        }
    }

    for (int i = 0; i < N; i++) {
        if (count(All(results[i]), true) == N) return i;
    }

    assert(false);    
}

} // namespace Solver1

namespace Solver2 {

const int N = 1'000'000;
const vector<int> steps = {500000, 250000, 125000, 62496, 20832, 3472, 183, 1};

int solve() {
    vector<int> candidates(N);
    iota(All(candidates), 0);

    for (auto st : steps) {
        int cur_sz = candidates.size();

        vector<int> sizes(st, cur_sz / st);
        for (int i = 0; i < cur_sz % st; i++) sizes[i]++;

        vector<vector<int>> sep;
        int t = 0;
        for (auto sz : sizes) {
            sep.push_back(vector(candidates.begin() + t, candidates.begin() + t + sz));
            t += sz;
        }

        vector<int> Q1, Q2;
        for (int i = 0; i < st; i++) {
            for (int j = 0; j < sizes[i]; j++) {
                for (int k = j+1; k < sizes[i]; k++) {
                    Q1.push_back(sep[i][j]); Q2.push_back(sep[i][k]);
                }
            }
        }
        
        vector<int> ans = ask(Q1, Q2);
        vector<int> new_candidates;
        for (int t = 0, i = 0; i < st; i++) {
            int sz = sizes[i];
            vector results(sz, vector(sz, false));
            for (int j = 0; j < sz; j++) {
                results[j][j] = true;
                for (int k = j+1; k < sz; k++) {
                    results[j][k] = (ans[t++] == sep[i][j]);
                    results[k][j] = 1 ^ results[j][k];
                }
            }
            for (int j = 0; j < sz; j++) {
                if (count(All(results[j]), true) == sz) {
                    new_candidates.push_back(sep[i][j]);
                    break;
                }
            }
        }

        swap(candidates, new_candidates);
    }

    return candidates[0];
}

} // namespace Solver2

int richest(int N, int T, int S) {
    if (N <= 1'000) return Solver1::solve();
    else return Solver2::solve();
}

#ifdef Zanite
static int N, T, S, r, t, s;
static vector<int> W;
vector<int> ask(vector<int> i, vector<int> j) {
    ++t;
    if (t > T)
        throw string("Too many queries");
    if (i.size() != j.size())
        throw string("Invalid query: i and j must have the same size");
    int m = i.size();
    s += m;
    if (s > S)
        throw string("Too many total elements in queries");
    vector<int> res(m);
    for (int k = 0; k < m; k++) {
        if (i[k] < 0 || i[k] >= N || j[k] < 0 || j[k] >= N)
            throw string("Invalid query: index out of bounds");
        res[k] = W[i[k]] > W[j[k]] ? i[k] : j[k];
    }
    return res;
}

constexpr int Sub2_score = 85;

int main() {
    int R;
    cin >> N >> T >> S >> R;
    if (N <= 0 || T < 0 || S < 0 || R < 0) {
        cerr << "Invalid input for N, T, S or R" << endl;
        return 1;
    }
    mt19937_64 rng(R);
    W.resize(N);
    bool hasWrong = false;
    int maxt = 0, maxs = 0;
    for (int _ = 0; _ < 1; _++) {
        iota(W.begin(), W.end(), 0);
        shuffle(W.begin(), W.end(), rng);
        int answer = max_element(W.begin(), W.end()) - W.begin();
        try {
            r = -1; t = 0; s = 0;
            r = richest(N, T, S);
            if (r != answer)
                throw string("Wrong Answer");
            cout << r << ' ' << t << ' ' << s << " Correct (pretest)" << endl;
        } catch (const string& msg) {
            hasWrong = true;
            cout << r << ' ' << t << ' ' << s << ' ' << msg << endl;
        }
        maxt = max(maxt, t);
        maxs = max(maxs, s);
    }
    if (N == 1000 && T == 1 && S == 499500) {
        if (hasWrong) {
            cout << "Wrong Case 1, score: 0 / " << (100 - Sub2_score) << endl;
        } else {
            cout << "Correct (pretest) Case 1, score: " << (100 - Sub2_score) << " / " << (100 - Sub2_score) << endl;
        }
    } else if (N == 1000000 && T == 20 && S == 2000000) {
        if (hasWrong) {
            cout << "Wrong Case 2, score: 0 / " << Sub2_score << endl;
        } else {
            double ft = 1;
            if (maxt > 8)
                ft -= sqrt(maxt - 8) / 4;
            double gs = 1;
            if (maxs > 1099944) {
            	if (maxs < 1100044)
            		gs -= log10(maxs - 1099943) / 6;
            	else
            		gs -= 1.0 / 3 + pow(maxs - 1100043, 1.0 / 2) / 1500;
			}
            cout
                << (ft * gs >= 1 ? "Correct" : "Partially correct")
                << " (pretest) Case 2, score: "
                << to_string(int(Sub2_score * ft * gs))
                << " / " << Sub2_score;
        }
    } else {
        if (hasWrong) {
            cout << "Wrong" << endl;
        } else {
            cout << "Correct" << endl;
        }
    }
}
#endif

// dibisakan

詳細信息


Pretests

Pretest #1:

score: 15
Accepted
time: 609ms
memory: 23832kb

input:

1000 1 499500 957319859

output:

Correct
7127326332295218295
1.000000
1331569654267968081

result:

points 1.0 Correct

Pretest #2:

score: 85
Accepted
time: 3002ms
memory: 101976kb

input:

1000000 20 2000000 29091473

output:

Correct Case 2, 85 / 85, maxt = 8, maxs = 1099944
7610580723948932399
1.000000
1331569654267968081

result:

points 1.0 Correct Case 2, 85 / 85, maxt = 8, maxs = 1099944


Final Tests

Test #1:

score: 15
Accepted
time: 616ms
memory: 23200kb

input:

1000 1 499500 957319857

output:

Correct
7127326332295218295
1.000000
1331569654267968081

result:

points 1.0 Correct

Test #2:

score: 85
Accepted
time: 3001ms
memory: 102164kb

input:

1000000 20 2000000 29091471

output:

Correct Case 2, 85 / 85, maxt = 8, maxs = 1099944
7610580723948932399
1.000000
1331569654267968081

result:

points 1.0 Correct Case 2, 85 / 85, maxt = 8, maxs = 1099944