結果
| 問題 |
No.5017 Tool-assisted Shooting
|
| ユーザー |
|
| 提出日時 | 2023-07-16 16:20:07 |
| 言語 | C++17(gcc12) (gcc 12.3.0 + boost 1.87.0) |
| 結果 |
RE
|
| 実行時間 | - |
| コード長 | 6,230 bytes |
| コンパイル時間 | 3,211 ms |
| コンパイル使用メモリ | 227,616 KB |
| 実行使用メモリ | 24,396 KB |
| スコア | 159,994 |
| 平均クエリ数 | 826.64 |
| 最終ジャッジ日時 | 2023-07-16 16:21:20 |
| 合計ジャッジ時間 | 24,977 ms |
|
ジャッジサーバーID (参考情報) |
judge12 / judge15 |
(要ログイン)
| ファイルパターン | 結果 |
|---|---|
| other | RE * 100 |
コンパイルメッセージ
コピーコンストラクタ ‘Input::Input(const Input&)’ 内,
inlined from ‘Solver::Solver(const Input&)’ at main.cpp:181:33,
inlined from ‘int main()’ at main.cpp:253:24:
main.cpp:56:8: 警告: ‘input.Input::p’ is used uninitialized [-Wuninitialized]
56 | struct Input {
| ^~~~~
main.cpp: 関数 ‘int main()’ 内:
main.cpp:251:11: 備考: ‘input’ はここで宣言されています
251 | Input input;
| ^~~~~
ソースコード
#pragma GCC optimize("O3")
#pragma GCC optimize("unroll-loops")
#include <bits/stdc++.h>
// #include <atcoder/all>
using namespace std;
// using namespace atcoder;
#define ll long long int
#define ull unsigned long long int
uniform_real_distribution<> uniform(0.0, 1.0);
struct Timer {
chrono::system_clock::time_point start;
void begin() {
start = chrono::system_clock::now();
}
double stopwatch() {
chrono::system_clock::time_point end = chrono::system_clock::now();
double elapsed = chrono::duration_cast<std::chrono::nanoseconds>(end - start).count();
elapsed *= 1e-9; // nanoseconds -> seconds
return elapsed;
}
bool yet(double time_limit) {
return stopwatch() < time_limit;
}
double progress(double time_limit) {
return stopwatch() / time_limit;
}
bool annealing_scheduler(double profit, mt19937& engine, double time_limit, double t0, double t1) {
assert(0.0 <= t1 && t1 <= t0);
if (profit >= 0.0) {
return true;
} else {
double ratio = progress(time_limit);
double t = pow(t0, 1.0 - ratio) * pow(t1, ratio);
return uniform(engine) < pow(2.0, profit/t);
}
}
};
constexpr double time_limit = 1.95;
constexpr int h = 60;
constexpr int w = 25;
constexpr int w_center = 12;
constexpr int max_turn = 1000;
constexpr tuple<int,int,int> none = {0, 0, 0};
struct Input {
bool online_judge = true;
array<int,w> p;
array<vector<tuple<int,int,int>>,max_turn> hpx;
int turn = 0;
void input(const string& filename) {
online_judge = false;
ifstream in(filename);
assert(in);
for (int y = 0; y < w; ++y) {
in >> p[y];
}
for (int turn = 0; turn < max_turn; ++turn) {
int n;
in >> n;
hpx[turn].resize(n);
for (int i = 0; i < n; ++i) {
int hi, pi, xi;
in >> hi >> pi >> xi;
hpx[turn][i] = {hi, pi, xi};
}
}
}
vector<tuple<int,int,int>> interact() {
++turn;
if (online_judge) {
int n;
cin >> n;
assert(n != -1);
vector<tuple<int,int,int>> ret(n);
for (int i = 0; i < n; ++i) {
int hi, pi, xi;
cin >> hi >> pi >> xi;
ret[i] = {hi, pi, xi};
}
return ret;
} else {
return hpx[turn - 1];
}
}
void print(int dy) {
assert(-1 <= dy && dy <= 1);
if (online_judge) {
cout << "LSR"[dy + 1] << endl;
}
}
};
struct State {
int offset;
int player;
array<array<tuple<int,int,int>,w>,h> grid; // {temporary HP, initial HP, power}
int s;
int score;
State() {
offset = 0;
player = w_center;
for (int x = 0; x < h; ++x) {
fill(grid[x].begin(), grid[x].end(), none);
}
s = 0;
score = 0;
}
bool move_opponents() {
assert(grid[offset][player] == none);
if (grid[(offset + 1) % h][player] != none) {
// game over
return true;
}
fill(grid[offset].begin(), grid[offset].end(), none);
++offset;
offset %= h;
return false;
}
void make_oppenents_appear(const vector<tuple<int,int,int>>& oppenents) {
int x = (offset - 1 + h) % h;
for (auto [hi, pi, yi] : oppenents) {
grid[x][yi] = {hi, hi, pi};
}
}
bool move_player(int dy) {
assert(grid[offset][player] == none);
player += dy;
player %= w;
return (grid[offset][player] != none);
}
void attack() {
int dx = get_lowest_opponent(player);
if (dx == -1) {
return;
}
get<0>(grid[(offset + dx) % h][player]) -= 1 + s / 100;
if (get<0>(grid[(offset + dx) % h][player]) <= 0) {
// destroy the oppenent
score += get<1>(grid[(offset + dx) % h][player]);
s += get<2>(grid[(offset + dx) % h][player]);
grid[(offset + dx) % h][player] = none;
}
}
int get_lowest_opponent(int y) {
for (int dx = 1; dx < h; ++dx) {
if (grid[(offset + dx) % h][y] != none) {
return dx;
}
}
return -1;
}
};
struct Solver {
Timer timer;
Input input;
State state;
Solver(const Input& input): input(input) {
timer.begin();
}
void solve() {
for (int turn = 0; turn < max_turn; ++turn) {
if (state.move_opponents()) {
break;
}
state.make_oppenents_appear(input.interact());
int dy = 0;
if (!can_move(dy)) {
dy = 1;
}
input.print(dy);
if (state.move_player(dy)) {
break;
}
state.attack();
}
}
bool can_move(int dy) {
State s = state;
if (s.move_player(dy)) {
return false;
}
if (s.move_opponents()) {
return false;
}
return true;
}
ll score() {
return state.score;
}
};
void multi_test(int cases) {
cerr << "cases: " << cases << endl;
long long sum_scores = 0.0;
for (int seed = 0; seed < cases; ++seed) {
string filename = "in/";
filename += '0' + seed / 1000;
filename += '0' + (seed / 100) % 10;
filename += '0' + (seed / 10) % 10;
filename += '0' + seed % 10;
filename += ".txt";
Timer timer;
timer.begin();
Input input;
input.input(filename);
Solver solver(input);
solver.solve();
cerr << filename << " " << solver.score() << " " << timer.stopwatch() << " sec" << endl;
sum_scores += solver.score();
}
cerr << "Average Score: " << sum_scores / cases << endl;
}
int main() {
Input input;
Solver solver(input);
solver.solve();
int cases = 100;
multi_test(cases);
return 0;
}