misc/fastio.hpp
- View this file on GitHub
- Last update: 2024-05-03 23:21:26+09:00
- Include:
#include "misc/fastio.hpp"
Depends on
Required by
Verified with
verify/verify-aoj-other/aoj-2995-hashmap.test.cpp
verify/verify-aoj-other/aoj-2995.test.cpp
verify/verify-unit-test/arbitrary-ntt-mod18446744069414584321.test.cpp
verify/verify-unit-test/bigint2.test.cpp
verify/verify-unit-test/bigint3.test.cpp
verify/verify-unit-test/fast-inv-o1.test.cpp
verify/verify-unit-test/garner-bigint.test.cpp
verify/verify-unit-test/radix-sort.test.cpp
verify/verify-unit-test/rbst-segment-tree.test.cpp
verify/verify-yosupo-ds/yosupo-dynamic-sequence-range-affine-range-sum-splay.test.cpp
verify/verify-yosupo-ds/yosupo-dynamic-sequence-range-affine-range-sum-treap.test.cpp
verify/verify-yosupo-ds/yosupo-dynamic-sequence-range-affine-range-sum.test.cpp
verify/verify-yosupo-ds/yosupo-dynamic-tree-subtree-add-subtree-sum.test.cpp
verify/verify-yosupo-ds/yosupo-dynamic-tree-vertex-add-path-sum.test.cpp
verify/verify-yosupo-ds/yosupo-dynamic-tree-vertex-add-subtree-sum-2.test.cpp
verify/verify-yosupo-ds/yosupo-dynamic-tree-vertex-add-subtree-sum.test.cpp
verify/verify-yosupo-ds/yosupo-dynamic-tree-vertex-set-path-composite.test.cpp
verify/verify-yosupo-ds/yosupo-hash-map-variable-length.test.cpp
verify/verify-yosupo-ds/yosupo-hashmap.test.cpp
verify/verify-yosupo-ds/yosupo-orderedmap.test.cpp
verify/verify-yosupo-ds/yosupo-point-add-rectangle-sum-abstruct-range-tree.test.cpp
verify/verify-yosupo-ds/yosupo-point-add-rectangle-sum-bit2d.test.cpp
verify/verify-yosupo-ds/yosupo-point-add-rectangle-sum-dseg2d.test.cpp
verify/verify-yosupo-ds/yosupo-point-add-rectangle-sum-rtree-fenwick.test.cpp
verify/verify-yosupo-ds/yosupo-point-add-rectangle-sum-segtree-on-wm.test.cpp
verify/verify-yosupo-ds/yosupo-point-add-rectangle-sum-wm.test.cpp
verify/verify-yosupo-ds/yosupo-predecessor-problem-vEB-tree.test.cpp
verify/verify-yosupo-ds/yosupo-predecessor-problem.test.cpp
verify/verify-yosupo-ds/yosupo-range-add-range-sum-linkcuttree.test.cpp
verify/verify-yosupo-ds/yosupo-rollback-union-find.test.cpp
verify/verify-yosupo-ds/yosupo-segtree-beats.test.cpp
verify/verify-yosupo-ds/yosupo-static-range-inversion-query-2.test.cpp
verify/verify-yosupo-ds/yosupo-static-range-inversions-query.test.cpp
verify/verify-yosupo-ds/yosupo-swag.test.cpp
verify/verify-yosupo-ds/yosupo-vertex-add-path-sum-euler-tour.test.cpp
verify/verify-yosupo-ds/yosupo-vertex-add-subtree-sum-dst-on-tree.test.cpp
verify/verify-yosupo-ds/yosupo-vertex-add-subtree-sum-euler-tree.test.cpp
verify/verify-yosupo-fps/yosupo-composition-fast.test.cpp
verify/verify-yosupo-fps/yosupo-composition.test.cpp
verify/verify-yosupo-fps/yosupo-division-of-polynomials.test.cpp
verify/verify-yosupo-fps/yosupo-exp-relaxed-convolution.test.cpp
verify/verify-yosupo-fps/yosupo-inv-of-polynomials.test.cpp
verify/verify-yosupo-fps/yosupo-inv-relaxed-convolution.test.cpp
verify/verify-yosupo-fps/yosupo-linear-recurrence.test.cpp
verify/verify-yosupo-fps/yosupo-sum-of-exp-poly-limit.test.cpp
verify/verify-yosupo-fps/yosupo-sum-of-exp-poly.test.cpp
verify/verify-yosupo-fps/yosupo-taylor-shift.test.cpp
verify/verify-yosupo-graph/yosupo-exp-of-set-power-series.test.cpp
verify/verify-yosupo-graph/yosupo-frequency-table-of-tree-distance.test.cpp
verify/verify-yosupo-graph/yosupo-lowest-common-ancestor-doubling.test.cpp
verify/verify-yosupo-graph/yosupo-lowest-common-ancestor-euler-tour.test.cpp
verify/verify-yosupo-graph/yosupo-lowest-common-ancestor-tree-util.test.cpp
verify/verify-yosupo-graph/yosupo-matching-on-bipartite-graph.test.cpp
verify/verify-yosupo-graph/yosupo-max-independent-set.test.cpp
verify/verify-yosupo-graph/yosupo-shortest-path-2.test.cpp
verify/verify-yosupo-graph/yosupo-shortest-path-3.test.cpp
verify/verify-yosupo-graph/yosupo-shortest-path-4.test.cpp
verify/verify-yosupo-math/yosupo-addition-of-big-integers.test.cpp
verify/verify-yosupo-math/yosupo-binomial-coefficient-large.test.cpp
verify/verify-yosupo-math/yosupo-enumerate-quotient.test.cpp
verify/verify-yosupo-math/yosupo-factorization.test.cpp
verify/verify-yosupo-math/yosupo-gcd-convolution.test.cpp
verify/verify-yosupo-math/yosupo-kth-root-integral.test.cpp
verify/verify-yosupo-math/yosupo-lcm-convolution.test.cpp
verify/verify-yosupo-math/yosupo-linear-equation-2.test.cpp
verify/verify-yosupo-math/yosupo-matrix-product-strassen.test.cpp
verify/verify-yosupo-math/yosupo-matrix-product-vectorize-modint.test.cpp
verify/verify-yosupo-math/yosupo-mod-log.test.cpp
verify/verify-yosupo-math/yosupo-multiplication-of-big-integers.test.cpp
verify/verify-yosupo-math/yosupo-nim-product.test.cpp
verify/verify-yosupo-math/yosupo-polynomial-composite-set-power-series.test.cpp
verify/verify-yosupo-math/yosupo-primality-test.test.cpp
verify/verify-yosupo-math/yosupo-prime-table.test.cpp
verify/verify-yosupo-math/yosupo-subset-convolution-fast.test.cpp
verify/verify-yosupo-math/yosupo-subset-convolution.test.cpp
verify/verify-yosupo-math/yosupo-tetration-mod.test.cpp
verify/verify-yosupo-ntt/yosupo-convolution-arbitrarylengthntt.test.cpp
verify/verify-yosupo-ntt/yosupo-convolution-large.test.cpp
verify/verify-yosupo-ntt/yosupo-convolution-real-fft-15bit.test.cpp
verify/verify-yosupo-ntt/yosupo-convolution-real-fft-toom-3.test.cpp
verify/verify-yosupo-ntt/yosupo-convolution-relaxed-convolution.test.cpp
verify/verify-yosupo-ntt/yosupo-inliner-multiply.test.cpp
verify/verify-yosupo-ntt/yosupo-multiplicative-convolution.test.cpp
verify/verify-yosupo-other/yosupo-a-plus-b-128bit-fastio.test.cpp
verify/verify-yosupo-other/yosupo-many-a-plus-b.test.cpp
Code
#pragma once
#include <cstdio>
#include <cstring>
#include <string>
#include <type_traits>
#include <utility>
using namespace std;
#include "../internal/internal-type-traits.hpp"
namespace fastio {
static constexpr int SZ = 1 << 17;
static constexpr int offset = 64;
char inbuf[SZ], outbuf[SZ];
int in_left = 0, in_right = 0, out_right = 0;
struct Pre {
char num[40000];
constexpr Pre() : num() {
for (int i = 0; i < 10000; i++) {
int n = i;
for (int j = 3; j >= 0; j--) {
num[i * 4 + j] = n % 10 + '0';
n /= 10;
}
}
}
} constexpr pre;
void load() {
int len = in_right - in_left;
memmove(inbuf, inbuf + in_left, len);
in_right = len + fread(inbuf + len, 1, SZ - len, stdin);
in_left = 0;
}
void flush() {
fwrite(outbuf, 1, out_right, stdout);
out_right = 0;
}
void skip_space() {
if (in_left + offset > in_right) load();
while (inbuf[in_left] <= ' ') in_left++;
}
void single_read(char& c) {
if (in_left + offset > in_right) load();
skip_space();
c = inbuf[in_left++];
}
void single_read(string& S) {
skip_space();
while (true) {
if (in_left == in_right) load();
int i = in_left;
for (; i != in_right; i++) {
if (inbuf[i] <= ' ') break;
}
copy(inbuf + in_left, inbuf + i, back_inserter(S));
in_left = i;
if (i != in_right) break;
}
}
template <typename T,
enable_if_t<internal::is_broadly_integral_v<T>>* = nullptr>
void single_read(T& x) {
if (in_left + offset > in_right) load();
skip_space();
char c = inbuf[in_left++];
[[maybe_unused]] bool minus = false;
if constexpr (internal::is_broadly_signed_v<T>) {
if (c == '-') minus = true, c = inbuf[in_left++];
}
x = 0;
while (c >= '0') {
x = x * 10 + (c & 15);
c = inbuf[in_left++];
}
if constexpr (internal::is_broadly_signed_v<T>) {
if (minus) x = -x;
}
}
void rd() {}
template <typename Head, typename... Tail>
void rd(Head& head, Tail&... tail) {
single_read(head);
rd(tail...);
}
void single_write(const char& c) {
if (out_right > SZ - offset) flush();
outbuf[out_right++] = c;
}
void single_write(const bool& b) {
if (out_right > SZ - offset) flush();
outbuf[out_right++] = b ? '1' : '0';
}
void single_write(const string& S) {
flush(), fwrite(S.data(), 1, S.size(), stdout);
}
void single_write(const char* p) { flush(), fwrite(p, 1, strlen(p), stdout); }
template <typename T,
enable_if_t<internal::is_broadly_integral_v<T>>* = nullptr>
void single_write(const T& _x) {
if (out_right > SZ - offset) flush();
if (_x == 0) {
outbuf[out_right++] = '0';
return;
}
T x = _x;
if constexpr (internal::is_broadly_signed_v<T>) {
if (x < 0) outbuf[out_right++] = '-', x = -x;
}
constexpr int buffer_size = sizeof(T) * 10 / 4;
char buf[buffer_size];
int i = buffer_size;
while (x >= 10000) {
i -= 4;
memcpy(buf + i, pre.num + (x % 10000) * 4, 4);
x /= 10000;
}
if (x < 100) {
if (x < 10) {
outbuf[out_right] = '0' + x;
++out_right;
} else {
uint32_t q = (uint32_t(x) * 205) >> 11;
uint32_t r = uint32_t(x) - q * 10;
outbuf[out_right] = '0' + q;
outbuf[out_right + 1] = '0' + r;
out_right += 2;
}
} else {
if (x < 1000) {
memcpy(outbuf + out_right, pre.num + (x << 2) + 1, 3);
out_right += 3;
} else {
memcpy(outbuf + out_right, pre.num + (x << 2), 4);
out_right += 4;
}
}
memcpy(outbuf + out_right, buf + i, buffer_size - i);
out_right += buffer_size - i;
}
void wt() {}
template <typename Head, typename... Tail>
void wt(const Head& head, const Tail&... tail) {
single_write(head);
wt(std::forward<const Tail>(tail)...);
}
template <typename... Args>
void wtn(const Args&... x) {
wt(std::forward<const Args>(x)...);
wt('\n');
}
struct Dummy {
Dummy() { atexit(flush); }
} dummy;
} // namespace fastio
using fastio::rd;
using fastio::skip_space;
using fastio::wt;
using fastio::wtn;#line 2 "misc/fastio.hpp"
#include <cstdio>
#include <cstring>
#include <string>
#include <type_traits>
#include <utility>
using namespace std;
#line 2 "internal/internal-type-traits.hpp"
#line 4 "internal/internal-type-traits.hpp"
using namespace std;
namespace internal {
template <typename T>
using is_broadly_integral =
typename conditional_t<is_integral_v<T> || is_same_v<T, __int128_t> ||
is_same_v<T, __uint128_t>,
true_type, false_type>::type;
template <typename T>
using is_broadly_signed =
typename conditional_t<is_signed_v<T> || is_same_v<T, __int128_t>,
true_type, false_type>::type;
template <typename T>
using is_broadly_unsigned =
typename conditional_t<is_unsigned_v<T> || is_same_v<T, __uint128_t>,
true_type, false_type>::type;
#define ENABLE_VALUE(x) \
template <typename T> \
constexpr bool x##_v = x<T>::value;
ENABLE_VALUE(is_broadly_integral);
ENABLE_VALUE(is_broadly_signed);
ENABLE_VALUE(is_broadly_unsigned);
#undef ENABLE_VALUE
#define ENABLE_HAS_TYPE(var) \
template <class, class = void> \
struct has_##var : false_type {}; \
template <class T> \
struct has_##var<T, void_t<typename T::var>> : true_type {}; \
template <class T> \
constexpr auto has_##var##_v = has_##var<T>::value;
#define ENABLE_HAS_VAR(var) \
template <class, class = void> \
struct has_##var : false_type {}; \
template <class T> \
struct has_##var<T, void_t<decltype(T::var)>> : true_type {}; \
template <class T> \
constexpr auto has_##var##_v = has_##var<T>::value;
} // namespace internal
#line 12 "misc/fastio.hpp"
namespace fastio {
static constexpr int SZ = 1 << 17;
static constexpr int offset = 64;
char inbuf[SZ], outbuf[SZ];
int in_left = 0, in_right = 0, out_right = 0;
struct Pre {
char num[40000];
constexpr Pre() : num() {
for (int i = 0; i < 10000; i++) {
int n = i;
for (int j = 3; j >= 0; j--) {
num[i * 4 + j] = n % 10 + '0';
n /= 10;
}
}
}
} constexpr pre;
void load() {
int len = in_right - in_left;
memmove(inbuf, inbuf + in_left, len);
in_right = len + fread(inbuf + len, 1, SZ - len, stdin);
in_left = 0;
}
void flush() {
fwrite(outbuf, 1, out_right, stdout);
out_right = 0;
}
void skip_space() {
if (in_left + offset > in_right) load();
while (inbuf[in_left] <= ' ') in_left++;
}
void single_read(char& c) {
if (in_left + offset > in_right) load();
skip_space();
c = inbuf[in_left++];
}
void single_read(string& S) {
skip_space();
while (true) {
if (in_left == in_right) load();
int i = in_left;
for (; i != in_right; i++) {
if (inbuf[i] <= ' ') break;
}
copy(inbuf + in_left, inbuf + i, back_inserter(S));
in_left = i;
if (i != in_right) break;
}
}
template <typename T,
enable_if_t<internal::is_broadly_integral_v<T>>* = nullptr>
void single_read(T& x) {
if (in_left + offset > in_right) load();
skip_space();
char c = inbuf[in_left++];
[[maybe_unused]] bool minus = false;
if constexpr (internal::is_broadly_signed_v<T>) {
if (c == '-') minus = true, c = inbuf[in_left++];
}
x = 0;
while (c >= '0') {
x = x * 10 + (c & 15);
c = inbuf[in_left++];
}
if constexpr (internal::is_broadly_signed_v<T>) {
if (minus) x = -x;
}
}
void rd() {}
template <typename Head, typename... Tail>
void rd(Head& head, Tail&... tail) {
single_read(head);
rd(tail...);
}
void single_write(const char& c) {
if (out_right > SZ - offset) flush();
outbuf[out_right++] = c;
}
void single_write(const bool& b) {
if (out_right > SZ - offset) flush();
outbuf[out_right++] = b ? '1' : '0';
}
void single_write(const string& S) {
flush(), fwrite(S.data(), 1, S.size(), stdout);
}
void single_write(const char* p) { flush(), fwrite(p, 1, strlen(p), stdout); }
template <typename T,
enable_if_t<internal::is_broadly_integral_v<T>>* = nullptr>
void single_write(const T& _x) {
if (out_right > SZ - offset) flush();
if (_x == 0) {
outbuf[out_right++] = '0';
return;
}
T x = _x;
if constexpr (internal::is_broadly_signed_v<T>) {
if (x < 0) outbuf[out_right++] = '-', x = -x;
}
constexpr int buffer_size = sizeof(T) * 10 / 4;
char buf[buffer_size];
int i = buffer_size;
while (x >= 10000) {
i -= 4;
memcpy(buf + i, pre.num + (x % 10000) * 4, 4);
x /= 10000;
}
if (x < 100) {
if (x < 10) {
outbuf[out_right] = '0' + x;
++out_right;
} else {
uint32_t q = (uint32_t(x) * 205) >> 11;
uint32_t r = uint32_t(x) - q * 10;
outbuf[out_right] = '0' + q;
outbuf[out_right + 1] = '0' + r;
out_right += 2;
}
} else {
if (x < 1000) {
memcpy(outbuf + out_right, pre.num + (x << 2) + 1, 3);
out_right += 3;
} else {
memcpy(outbuf + out_right, pre.num + (x << 2), 4);
out_right += 4;
}
}
memcpy(outbuf + out_right, buf + i, buffer_size - i);
out_right += buffer_size - i;
}
void wt() {}
template <typename Head, typename... Tail>
void wt(const Head& head, const Tail&... tail) {
single_write(head);
wt(std::forward<const Tail>(tail)...);
}
template <typename... Args>
void wtn(const Args&... x) {
wt(std::forward<const Args>(x)...);
wt('\n');
}
struct Dummy {
Dummy() { atexit(flush); }
} dummy;
} // namespace fastio
using fastio::rd;
using fastio::skip_space;
using fastio::wt;
using fastio::wtn;