QOJ.ac
QOJ
ID | Problem | Submitter | Result | Time | Memory | Language | File size | Submit time | Judge time |
---|---|---|---|---|---|---|---|---|---|
#601509 | #7775. 【模板】矩阵快速幂 | nhuang685 | 0 | 124ms | 235544kb | C++23 | 8.7kb | 2024-09-30 03:22:41 | 2024-09-30 03:22:41 |
Judging History
answer
/**
* @author n685
* @brief
* @date 2024-09-20 21:20:01
*
*
*/
#ifndef LOCAL
#pragma GCC optimize("O3,unroll-loops")
// #pragma GCC target("avx2,bmi,bmi2,lzcnt,popcnt")
#endif
#include "bits/stdc++.h"
#ifdef LOCAL
#include "dd/debug.h"
#else
#define dbg(...) 42
#define dbg_proj(...) 420
#define dbg_rproj(...) 420420
void nline() {}
void bar() {}
void start_clock() {}
void end_clock() {}
#endif
using i128 = __int128_t;
namespace rs = std::ranges;
namespace rv = std::views;
constexpr int MOD = 998'244'353;
using i128 = __int128_t;
template <class T>
concept integral = std::integral<T> || std::is_same_v<i128, T>;
// based on https://cp-algorithms.com/algebra/big-integer.html
struct BigInt {
static constexpr int LG = 9;
static constexpr int BASE = []() -> int {
int ans = 1;
for (int i = 0; i < LG; ++i) {
ans *= 10;
}
return ans;
}();
std::vector<int> a;
BigInt() = default;
explicit BigInt(integral auto val) {
while (val > 0) {
a.push_back(static_cast<int>(val % BASE));
val /= BASE;
}
}
explicit BigInt(const std::string &s) {
for (int i = static_cast<int>(s.size()) - 1; i >= 0; i -= BASE) {
if (i < LG) {
a.push_back(std::stoi(s.substr(0, i + 1)));
} else {
a.push_back(std::stoi(s.substr(i - LG + 1, LG)));
}
}
}
friend std::istream &operator>>(std::istream &in, BigInt &val) {
std::string s;
in >> s;
val = BigInt{s};
return in;
}
friend std::ostream &operator<<(std::ostream &out, const BigInt &val) {
for (int i : val.a | rv::reverse) {
out << i;
}
return out;
}
void trim() {
while (!a.empty() && a.back() == 0) {
a.pop_back();
}
}
BigInt &operator+=(const BigInt &rhs) {
int carry = 0;
for (int i = 0; i < std::max(std::ssize(a), std::ssize(rhs.a)); ++i) {
if (i == std::ssize(a)) {
a.push_back(0);
}
a[i] += carry + (i < std::ssize(rhs.a) ? rhs.a[i] : 0);
carry = (a[i] >= BASE) ? 1 : 0;
if (a[i] >= BASE) {
a[i] -= BASE;
}
}
return *this;
}
BigInt &operator-=(const BigInt &rhs) {
int carry = 0;
for (int i = 0; i < std::ssize(rhs.a) || carry > 0; ++i) {
a[i] -= carry + (i < std::ssize(rhs.a) ? rhs.a[i] : 0);
carry = (a[i] < 0) ? 1 : 0;
if (a[i] < 0) {
a[i] += BASE;
}
}
trim();
return *this;
}
BigInt &operator*=(int rhs) {
assert(rhs < BASE);
int carry = 0;
for (int i = 0; i < std::ssize(a) || carry > 0; ++i) {
if (i == std::ssize(a)) {
a.push_back(0);
}
int64_t cur = carry + int64_t{a[i]} * rhs;
a[i] = static_cast<int>(cur % BASE);
carry = static_cast<int>(cur / BASE);
}
return *this;
}
friend BigInt operator*(const BigInt &lhs, const BigInt &rhs) {
BigInt ans;
ans.a.resize(lhs.a.size() + rhs.a.size());
for (int i = 0; i < std::ssize(lhs.a); ++i) {
for (int j = 0, carry = 0; j < std::ssize(rhs.a) || carry > 0; ++j) {
int64_t cur = ans.a[i + j]
+ int64_t{lhs.a[i]} * (j < std::ssize(rhs.a) ? rhs.a[j] : 0) + carry;
ans.a[i + j] = static_cast<int>(cur % BASE);
carry = static_cast<int>(cur / BASE);
}
}
ans.trim();
return ans;
}
BigInt &operator*=(const BigInt &rhs) { return *this = *this * rhs; }
int div_mod(int rhs) {
int carry = 0;
for (int i = static_cast<int>(a.size()) - 1; i >= 0; --i) {
int64_t cur = a[i] + int64_t{carry} * BASE;
a[i] = static_cast<int>(cur / rhs);
carry = static_cast<int>(cur % rhs);
}
trim();
return carry;
}
BigInt &operator/=(int rhs) {
div_mod(rhs);
return *this;
}
int operator%(int rhs) {
int carry = 0;
for (int i = static_cast<int>(a.size()) - 1; i >= 0; --i) {
carry = static_cast<int>((a[i] + int64_t{carry} * BASE) % rhs);
}
return carry;
}
bool operator==(const BigInt &rhs) const = default;
bool operator!=(const BigInt &rhs) const = default;
auto operator<=>(const BigInt &rhs) const {
if (a.size() != rhs.a.size()) {
return a.size() <=> rhs.a.size();
}
for (int i = static_cast<int>(a.size()) - 1; i >= 0; --i) {
if (a[i] != rhs.a[i]) {
return a[i] <=> rhs.a[i];
}
}
return std::strong_ordering::equal;
}
};
BigInt operator+(BigInt a, const BigInt &b) { return a += b; }
BigInt operator-(BigInt a, const BigInt &b) { return a -= b; }
BigInt operator*(BigInt a, int b) { return a *= b; }
BigInt operator*(int b, BigInt a) { return a *= b; }
#if defined(LOCAL) && __cplusplus >= 202302L
template <> struct std::formatter<BigInt, char> {
std::formatter<std::string, char> underlying;
constexpr formatter() {
if constexpr (requires { underlying.set_debug_format(); }) {
underlying.set_debug_format();
}
}
template <class ParseContext> constexpr auto parse(ParseContext &ctx) {
return underlying.parse(ctx);
}
template <class FormatContext>
auto format(const BigInt &val, FormatContext &ctx) const {
return underlying.format(std::stringstream{} << val, ctx);
}
};
#endif
template <class T> constexpr T INF = T{};
template <std::floating_point T>
constexpr T INF<T> = std::numeric_limits<T>::infinity();
template <> constexpr int INF<int> = 0x3f3f3f3f; // 1061109567
template <>
constexpr int64_t INF<int64_t> = 0x3f3f3f3f3f3f3f3f; // 4557430888798830399
template <>
constexpr i128 INF<i128> = (static_cast<i128>(INF<int64_t>) << 64)
| INF<int64_t>; // 84069761239290679208598432424319205183
struct Edge {
int u, v;
i128 w;
};
clock_t tot = 0;
clock_t tot2 = 0;
clock_t tot3 = 0;
void solve() {
static_assert(integral<i128>);
int n, m;
std::string sk;
std::cin >> n >> m >> sk;
BigInt k(sk);
std::vector<Edge> edges(m);
for (auto &[u, v, w] : edges) {
int64_t ww;
std::cin >> u >> v >> ww;
--u;
--v;
w = ww;
}
std::vector dist(n + 1, std::vector(n, std::vector<i128>(n, INF<i128>)));
std::vector d0(10 * n * n + 1, std::vector<i128>(n, INF<i128>));
d0[0][0] = 0;
for (int i = 0; i < n; ++i) {
dist[0][i][i] = 0;
}
for (int i = 1; i <= n; ++i) {
for (int j = 0; j < n; ++j) {
for (auto &[u, v, w] : edges) {
dist[i][j][v] = std::min(dist[i][j][v], dist[i - 1][j][u] + w);
}
}
d0[i] = dist[i][0];
}
for (int i = n + 1; i <= 10 * n * n; ++i) {
for (auto &[u, v, w] : edges) {
d0[i][v] = std::min(d0[i][v], d0[i - 1][u] + w);
}
}
if (k <= BigInt{10 * n * n}) {
int kk = std::stoi(sk);
for (int i = 0; i < n; ++i) {
if (d0[kk][i] == INF<i128>) {
std::cout << "-1 ";
} else {
std::cout << static_cast<int>(d0[kk][i] % MOD) << ' ';
}
}
std::cout << '\n';
return;
}
std::vector dp(n * n + 1, std::vector<BigInt>(n));
std::vector isinf(n * n + 1, std::vector<bool>(n, true));
for (int i = 0; i < n; ++i) {
i128 mi = INF<i128> / n;
int sz = 1;
for (int j = 1; j <= n; ++j) {
if (dist[j][i][i] != INF<i128> && dist[j][i][i] * sz < mi * j) {
mi = dist[j][i][i];
sz = j;
}
}
if (mi == INF<i128> / n) {
continue;
}
for (int j = n * n - n; j <= n * n; ++j) {
if (d0[j][i] == INF<i128>) {
continue;
}
BigInt times = k - BigInt{j + n * n};
int rem = times.div_mod(sz);
int rest = n * n;
if (rem > 0) {
times += BigInt{1};
rest -= sz - rem;
}
BigInt res = times * BigInt{mi} + BigInt{d0[j][i]};
if (isinf[rest][i]) {
dp[rest][i] = res;
} else {
dp[rest][i] = std::min(dp[rest][i], res);
}
isinf[rest][i] = false;
}
}
std::vector<std::tuple<int, int, BigInt>> edges2;
edges2.reserve(edges.size());
for (auto [u, v, w] : edges) {
edges2.emplace_back(u, v, w);
}
for (int i = n * n - 1; i >= 0; --i) {
for (const auto &[u, v, w] : edges2) {
if (!isinf[i + 1][u]) {
if (isinf[i][v]) {
dp[i][v] = dp[i + 1][u] + w;
} else {
dp[i][v] = std::min(dp[i][v], dp[i + 1][u] + w);
}
isinf[i][v] = false;
}
}
}
for (int i = 0; i < n; ++i) {
if (isinf[0][i]) {
std::cout << "-1 ";
} else {
std::cout << dp[0][i] % MOD << ' ';
}
}
std::cout << '\n';
}
int main() {
#ifndef LOCAL
std::ios::sync_with_stdio(false);
std::cin.tie(nullptr);
#endif
// std::freopen("input.txt", "r", stdin);
int s, t;
std::cin >> s >> t;
for (int i = 0; i < t; ++i) {
solve();
}
}
Details
Tip: Click on the bar to expand more detailed information
Subtask #1:
score: 0
Wrong Answer
Test #1:
score: 0
Wrong Answer
time: 124ms
memory: 235544kb
input:
1 1 100 101 899539897889989959 74 35 910832669819965536 35 85 910832669819965536 85 88 910832669819965536 88 30 910832669819965536 30 58 910832669819965536 58 60 910832669819965536 60 34 910832669819965536 34 8 910832669819965536 8 67 910832669819965536 67 89 910832669819965536 89 32 910832669819965...
output:
851410604 851410593 851410595 851410651 851410605 851410601 851410566 851410644 851410657 851410567 851410635 851410585 851410565 851410612 851410594 851410575 851410659 851410573 851410606 851410603 851410598 851410633 851410610 851410577 851410584 851410582 851410569 851410631 851410655 851410640 ...
result:
wrong answer 1st numbers differ - expected: '395495792', found: '851410604'
Subtask #2:
score: 0
Memory Limit Exceeded
Test #7:
score: 0
Memory Limit Exceeded
input:
2 1 300 598 8179377797889487867988994778539839593376697796496698959964978969 1 2 977880533270721156 2 1 977880533270721156 2 3 977880533270721156 3 2 977880533270721156 3 4 977880533270721156 4 3 977880533270721156 4 5 977880533270721156 5 4 977880533270721156 5 6 977880533270721156 6 5 977880533270...
output:
-1 911567081 -1 911556919 -1 911546757 -1 911536595 -1 911526433 -1 911516271 -1 911506109 -1 911495947 -1 911485785 -1 911475623 -1 911465461 -1 911455299 -1 911445137 -1 911434975 -1 911424813 -1 911414651 -1 911404489 -1 911394327 -1 911384165 -1 911374003 -1 911363841 -1 911353679 -1 911343517 -...
result:
Subtask #3:
score: 0
Skipped
Dependency #2:
0%
Subtask #4:
score: 0
Skipped
Dependency #1:
0%
Subtask #5:
score: 0
Skipped
Dependency #1:
0%
Subtask #6:
score: 0
Skipped
Dependency #3:
0%