結果

問題 No.1864 Shortest Paths Counting
ユーザー nok0nok0
提出日時 2022-03-04 22:29:58
言語 C++17
(gcc 12.3.0 + boost 1.83.0)
結果
WA  
実行時間 -
コード長 46,429 bytes
コンパイル時間 3,171 ms
コンパイル使用メモリ 232,284 KB
実行使用メモリ 167,580 KB
最終ジャッジ日時 2023-09-26 01:37:06
合計ジャッジ時間 7,430 ms
ジャッジサーバーID
(参考情報)
judge11 / judge13
このコードへのチャレンジ
(要ログイン)

テストケース

テストケース表示
入力 結果 実行時間
実行使用メモリ
testcase_00 AC 2 ms
8,760 KB
testcase_01 AC 2 ms
4,384 KB
testcase_02 WA -
testcase_03 WA -
testcase_04 WA -
testcase_05 AC 1 ms
4,380 KB
testcase_06 AC 2 ms
4,376 KB
testcase_07 AC 2 ms
4,380 KB
testcase_08 AC 1 ms
4,376 KB
testcase_09 TLE -
testcase_10 -- -
testcase_11 -- -
testcase_12 -- -
testcase_13 -- -
testcase_14 -- -
testcase_15 -- -
testcase_16 -- -
testcase_17 -- -
testcase_18 -- -
testcase_19 -- -
testcase_20 -- -
testcase_21 -- -
testcase_22 -- -
testcase_23 -- -
testcase_24 -- -
testcase_25 -- -
testcase_26 -- -
権限があれば一括ダウンロードができます
コンパイルメッセージ
template/macro.hpp:3: 警告: "all" が再定義されました
/Users/nok0/Documents/Programming/nok0/cftemp.hpp:32: 備考: ここが以前の宣言がある位置です

ソースコード

diff #

#line 1 "/Users/nok0/Documents/Programming/nok0/cftemp.hpp"
#include <bits/stdc++.h>
using namespace std;

#pragma region Macros
// rep macro
#define foa(v, a) for(auto &v : a)
#define REPname(a, b, c, d, e, ...) e
#define REP(...) REPname(__VA_ARGS__, REP3, REP2, REP1, REP0)(__VA_ARGS__)
#define REP0(x) for(int i = 0; i < (x); ++i)
#define REP1(i, x) for(int i = 0; i < (x); ++i)
#define REP2(i, l, r) for(int i = (l); i < (r); ++i)
#define REP3(i, l, r, c) for(int i = (l); i < (r); i += (c))
#define REPSname(a, b, c, ...) c
#define REPS(...) REPSname(__VA_ARGS__, REPS1, REPS0)(__VA_ARGS__)
#define REPS0(x) for(int i = 1; i <= (x); ++i)
#define REPS1(i, x) for(int i = 1; i <= (x); ++i)
#define RREPname(a, b, c, d, e, ...) e
#define RREP(...) RREPname(__VA_ARGS__, RREP3, RREP2, RREP1, RREP0)(__VA_ARGS__)
#define RREP0(x) for(int i = (x)-1; i >= 0; --i)
#define RREP1(i, x) for(int i = (x)-1; i >= 0; --i)
#define RREP2(i, r, l) for(int i = (r)-1; i >= (l); --i)
#define RREP3(i, r, l, c) for(int i = (r)-1; i >= (l); i -= (c))
#define RREPSname(a, b, c, ...) c
#define RREPS(...) RREPSname(__VA_ARGS__, RREPS1, RREPS0)(__VA_ARGS__)
#define RREPS0(x) for(int i = (x); i >= 1; --i)
#define RREPS1(i, x) for(int i = (x); i >= 1; --i)

// name macro
#define pb push_back
#define eb emplace_back
#define SZ(x) ((int)(x).size())
#define all(x) (x).begin(), (x).end()
#define rall(x) (x).rbegin(), (x).rend()
#define popcnt(x) __builtin_popcountll(x)
template <class T = int>
using V = std::vector<T>;
template <class T = int>
using VV = std::vector<std::vector<T>>;
template <class T>
using pqup = std::priority_queue<T, std::vector<T>, std::greater<T>>;
using ll = long long;
using ld = long double;
using int128 = __int128_t;
using pii = std::pair<int, int>;
using pll = std::pair<long long, long long>;

// input macro
template <class T, class U>
std::istream &operator>>(std::istream &is, std::pair<T, U> &p) {
	is >> p.first >> p.second;
	return is;
}
template <class T>
std::istream &operator>>(std::istream &is, std::vector<T> &v) {
	for(T &i : v) is >> i;
	return is;
}
std::istream &operator>>(std::istream &is, __int128_t &a) {
	std::string s;
	is >> s;
	__int128_t ret = 0;
	for(int i = 0; i < s.length(); i++)
		if('0' <= s[i] and s[i] <= '9')
			ret = 10 * ret + s[i] - '0';
	a = ret * (s[0] == '-' ? -1 : 1);
	return is;
}
namespace scanner {
void scan(int &a) { std::cin >> a; }
void scan(long long &a) { std::cin >> a; }
void scan(std::string &a) { std::cin >> a; }
void scan(char &a) { std::cin >> a; }
void scan(char a[]) { std::scanf("%s", a); }
void scan(double &a) { std::cin >> a; }
void scan(long double &a) { std::cin >> a; }
template <class T, class U>
void scan(std::pair<T, U> &p) { std::cin >> p; }
template <class T>
void scan(std::vector<T> &a) { std::cin >> a; }
void INPUT() {}
template <class Head, class... Tail>
void INPUT(Head &head, Tail &...tail) {
	scan(head);
	INPUT(tail...);
}
}  // namespace scanner
#define VEC(type, name, size)     \
	std::vector<type> name(size); \
	scanner::INPUT(name)
#define VVEC(type, name, h, w)                                    \
	std::vector<std::vector<type>> name(h, std::vector<type>(w)); \
	scanner::INPUT(name)
#define INT(...)     \
	int __VA_ARGS__; \
	scanner::INPUT(__VA_ARGS__)
#define LL(...)            \
	long long __VA_ARGS__; \
	scanner::INPUT(__VA_ARGS__)
#define STR(...)             \
	std::string __VA_ARGS__; \
	scanner::INPUT(__VA_ARGS__)
#define CHAR(...)     \
	char __VA_ARGS__; \
	scanner::INPUT(__VA_ARGS__)
#define DOUBLE(...)     \
	double __VA_ARGS__; \
	scanner::INPUT(__VA_ARGS__)
#define LD(...)              \
	long double __VA_ARGS__; \
	scanner::INPUT(__VA_ARGS__)

// output-macro
template <class T, class U>
std::ostream &operator<<(std::ostream &os, const std::pair<T, U> &p) {
	os << p.first << " " << p.second;
	return os;
}
template <class T>
std::ostream &operator<<(std::ostream &os, const std::vector<T> &a) {
	for(int i = 0; i < int(a.size()); ++i) {
		if(i) os << " ";
		os << a[i];
	}
	return os;
}
std::ostream &operator<<(std::ostream &dest, __int128_t &value) {
	std::ostream::sentry s(dest);
	if(s) {
		__uint128_t tmp = value < 0 ? -value : value;
		char buffer[128];
		char *d = std::end(buffer);
		do {
			--d;
			*d = "0123456789"[tmp % 10];
			tmp /= 10;
		} while(tmp != 0);
		if(value < 0) {
			--d;
			*d = '-';
		}
		int len = std::end(buffer) - d;
		if(dest.rdbuf()->sputn(d, len) != len) {
			dest.setstate(std::ios_base::badbit);
		}
	}
	return dest;
}
template <class T>
void print(const T a) { std::cout << a << '\n'; }
template <class Head, class... Tail>
void print(Head H, Tail... T) {
	std::cout << H << ' ';
	print(T...);
}
template <class T>
void printel(const T a) { std::cout << a << '\n'; }
template <class T>
void printel(const std::vector<T> &a) {
	for(const auto &v : a)
		std::cout << v << '\n';
}
template <class Head, class... Tail>
void printel(Head H, Tail... T) {
	std::cout << H << '\n';
	printel(T...);
}
void Yes(const bool b = true) { std::cout << (b ? "Yes\n" : "No\n"); }
void No() { std::cout << "No\n"; }
void YES(const bool b = true) { std::cout << (b ? "YES\n" : "NO\n"); }
void NO() { std::cout << "NO\n"; }
void err(const bool b = true) {
	if(b) {
		std::cout << "-1\n", exit(0);
	}
}

//debug macro
namespace debugger {
template <class T>
void view(const std::vector<T> &a) {
	std::cerr << "{ ";
	for(const auto &v : a) {
		std::cerr << v << ", ";
	}
	std::cerr << "\b\b }";
}
template <class T>
void view(const std::vector<std::vector<T>> &a) {
	std::cerr << "{\n";
	for(const auto &v : a) {
		std::cerr << "\t";
		view(v);
		std::cerr << "\n";
	}
	std::cerr << "}";
}
template <class T, class U>
void view(const std::vector<std::pair<T, U>> &a) {
	std::cerr << "{\n";
	for(const auto &p : a) std::cerr << "\t(" << p.first << ", " << p.second << ")\n";
	std::cerr << "}";
}
template <class T, class U>
void view(const std::map<T, U> &m) {
	std::cerr << "{\n";
	for(const auto &p : m) std::cerr << "\t[" << p.first << "] : " << p.second << "\n";
	std::cerr << "}";
}
template <class T, class U>
void view(const std::pair<T, U> &p) { std::cerr << "(" << p.first << ", " << p.second << ")"; }
template <class T>
void view(const std::set<T> &s) {
	std::cerr << "{ ";
	for(auto &v : s) {
		view(v);
		std::cerr << ", ";
	}
	std::cerr << "\b\b }";
}

template <class T>
void view(const T &e) { std::cerr << e; }
}  // namespace debugger
#ifdef LOCAL
void debug_out() {}
template <typename Head, typename... Tail>
void debug_out(Head H, Tail... T) {
	debugger::view(H);
	std::cerr << ", ";
	debug_out(T...);
}
#define debug(...)                                                \
	do {                                                          \
		std::cerr << __LINE__ << " [" << #__VA_ARGS__ << "] : ["; \
		debug_out(__VA_ARGS__);                                   \
		std::cerr << "\b\b]\n";                                   \
	} while(false)
#else
#define debug(...) (void(0))
#endif

// vector macro
template <class T>
int lb(const std::vector<T> &a, const T x) { return std::distance((a).begin(), std::lower_bound((a).begin(), (a).end(), (x))); }
template <class T>
int ub(const std::vector<T> &a, const T x) { return std::distance((a).begin(), std::upper_bound((a).begin(), (a).end(), (x))); }
template <class T>
void UNIQUE(std::vector<T> &a) {
	std::sort(a.begin(), a.end());
	a.erase(std::unique(a.begin(), a.end()), a.end());
}
template <class T>
std::vector<T> press(std::vector<T> &a) {
	auto res = a;
	UNIQUE(res);
	for(auto &v : a)
		v = lb(res, v);
	return res;
}
#define SORTname(a, b, c, ...) c
#define SORT(...) SORTname(__VA_ARGS__, SORT1, SORT0, ...)(__VA_ARGS__)
#define SORT0(a) std::sort((a).begin(), (a).end())
#define SORT1(a, c) std::sort((a).begin(), (a).end(), [](const auto x, const auto y) { return x c y; })
template <class T>
void ADD(std::vector<T> &a, const T x = 1) {
	for(auto &v : a) v += x;
}
template <class T>
void SUB(std::vector<T> &a, const T x = 1) {
	for(auto &v : a) v -= x;
}
std::vector<std::pair<char, int>> rle(const string &s) {
	int n = s.size();
	std::vector<std::pair<char, int>> ret;
	for(int l = 0; l < n;) {
		int r = l + 1;
		for(; r < n and s[l] == s[r]; r++) {}
		ret.emplace_back(s[l], r - l);
		l = r;
	}
	return ret;
}
template <class T>
std::vector<std::pair<T, int>> rle(const std::vector<T> &v) {
	int n = v.size();
	std::vector<std::pair<T, int>> ret;
	for(int l = 0; l < n;) {
		int r = l + 1;
		for(; r < n and v[l] == v[r]; r++) {}
		ret.emplace_back(v[l], r - l);
		l = r;
	}
	return ret;
}
std::vector<int> iota(int n) {
	std::vector<int> p(n);
	std::iota(p.begin(), p.end(), 0);
	return p;
}
template <class T>
struct cum_vector {
public:
	cum_vector() = default;
	template <class U>
	cum_vector(const std::vector<U> &vec) : cum((int)vec.size() + 1) {
		for(int i = 0; i < (int)vec.size(); i++)
			cum[i + 1] = cum[i] + vec[i];
	}
	T prod(int l, int r) {
		return cum[r] - cum[l];
	}

private:
	std::vector<T> cum;
};

// math macro
template <class T, class U>
inline bool chmin(T &a, const U &b) { return a > b ? a = b, true : false; }
template <class T, class U>
inline bool chmax(T &a, const U &b) { return a < b ? a = b, true : false; }
template <class T>
T divup(T x, T y) { return (x + y - 1) / y; }
template <class T>
T POW(T a, long long n) {
	T ret = 1;
	while(n) {
		if(n & 1) ret *= a;
		a *= a;
		n >>= 1;
	}
	return ret;
}
// modpow
long long POW(long long a, long long n, const int mod) {
	long long ret = 1;
	a = (a % mod + mod) % mod;
	while(n) {
		if(n & 1) (ret *= a) %= mod;
		(a *= a) %= mod;
		n >>= 1;
	}
	return ret;
}
template <class T, class F>
T bin_search(T ok, T ng, const F &f) {
	while(abs(ok - ng) > 1) {
		T mid = (ok + ng) >> 1;
		(f(mid) ? ok : ng) = mid;
	}
	return ok;
}
template <class T, class F>
T bin_search(T ok, T ng, const F &f, int loop) {
	for(int i = 0; i < loop; i++) {
		T mid = (ok + ng) / 2;
		(f(mid) ? ok : ng) = mid;
	}
	return ok;
}

// others
struct fast_io {
	fast_io() {
		ios::sync_with_stdio(false);
		cin.tie(nullptr);
		cout << fixed << setprecision(15);
	}
} fast_io_;
const int inf = 1e9;
const ll INF = 1e18;
#pragma endregion

void main_();

int main() {
	main_();
	return 0;
}
#line 2 "e.cpp"

namespace Nyaan {
using ll = long long;
using i64 = long long;
using u64 = unsigned long long;
using i128 = __int128_t;
using u128 = __uint128_t;

template <typename T>
using V = vector<T>;
template <typename T>
using VV = vector<vector<T>>;
using vi = vector<int>;
using vl = vector<long long>;
using vd = V<double>;
using vs = V<string>;
using vvi = vector<vector<int>>;
using vvl = vector<vector<long long>>;

template <typename T, typename U>
struct P : pair<T, U> {
	template <typename... Args>
	P(Args... args) : pair<T, U>(args...) {}

	using pair<T, U>::first;
	using pair<T, U>::second;

	T &x() { return first; }
	const T &x() const { return first; }
	U &y() { return second; }
	const U &y() const { return second; }

	P &operator+=(const P &r) {
		first += r.first;
		second += r.second;
		return *this;
	}
	P &operator-=(const P &r) {
		first -= r.first;
		second -= r.second;
		return *this;
	}
	P &operator*=(const P &r) {
		first *= r.first;
		second *= r.second;
		return *this;
	}
	P operator+(const P &r) const { return P(*this) += r; }
	P operator-(const P &r) const { return P(*this) -= r; }
	P operator*(const P &r) const { return P(*this) *= r; }
};

using pl = P<ll, ll>;
using pi = P<int, int>;
using vp = V<pl>;

constexpr int inf = 1001001001;
constexpr long long infLL = 4004004004004004004LL;

template <typename T>
int sz(const T &t) {
	return t.size();
}

template <typename T, typename U>
inline bool amin(T &x, U y) {
	return (y < x) ? (x = y, true) : false;
}
template <typename T, typename U>
inline bool amax(T &x, U y) {
	return (x < y) ? (x = y, true) : false;
}

template <typename T>
inline T Max(const vector<T> &v) {
	return *max_element(begin(v), end(v));
}
template <typename T>
inline T Min(const vector<T> &v) {
	return *min_element(begin(v), end(v));
}
template <typename T>
inline long long Sum(const vector<T> &v) {
	return accumulate(begin(v), end(v), 0LL);
}

template <typename T>
int lb(const vector<T> &v, const T &a) {
	return lower_bound(begin(v), end(v), a) - begin(v);
}
template <typename T>
int ub(const vector<T> &v, const T &a) {
	return upper_bound(begin(v), end(v), a) - begin(v);
}

constexpr long long TEN(int n) {
	long long ret = 1, x = 10;
	for(; n; x *= x, n >>= 1) ret *= (n & 1 ? x : 1);
	return ret;
}

template <typename T, typename U>
pair<T, U> mkp(const T &t, const U &u) {
	return make_pair(t, u);
}

template <typename T>
vector<T> mkrui(const vector<T> &v, bool rev = false) {
	vector<T> ret(v.size() + 1);
	if(rev) {
		for(int i = int(v.size()) - 1; i >= 0; i--) ret[i] = v[i] + ret[i + 1];
	} else {
		for(int i = 0; i < int(v.size()); i++) ret[i + 1] = ret[i] + v[i];
	}
	return ret;
};

template <typename T>
vector<T> mkuni(const vector<T> &v) {
	vector<T> ret(v);
	sort(ret.begin(), ret.end());
	ret.erase(unique(ret.begin(), ret.end()), ret.end());
	return ret;
}

template <typename F>
vector<int> mkord(int N, F f) {
	vector<int> ord(N);
	iota(begin(ord), end(ord), 0);
	sort(begin(ord), end(ord), f);
	return ord;
}

template <typename T>
vector<int> mkinv(vector<T> &v) {
	int max_val = *max_element(begin(v), end(v));
	vector<int> inv(max_val + 1, -1);
	for(int i = 0; i < (int)v.size(); i++) inv[v[i]] = i;
	return inv;
}

}  // namespace Nyaan
#line 58 "template/template.hpp"

// bit operation
#line 1 "template/bitop.hpp"
namespace Nyaan {
__attribute__((target("popcnt"))) inline int popcnt(const u64 &a) {
	return __builtin_popcount(a);
}
inline int lsb(const u64 &a) { return a ? __builtin_ctzll(a) : 64; }
inline int ctz(const u64 &a) { return a ? __builtin_ctzll(a) : 64; }
inline int msb(const u64 &a) { return a ? 63 - __builtin_clzll(a) : -1; }
template <typename T>
inline int gbit(const T &a, int i) {
	return (a >> i) & 1;
}
template <typename T>
inline void sbit(T &a, int i, bool b) {
	if(gbit(a, i) != b) a ^= T(1) << i;
}
constexpr long long PW(int n) { return 1LL << n; }
constexpr long long MSK(int n) { return (1LL << n) - 1; }
}  // namespace Nyaan
#line 61 "template/template.hpp"

// inout
#line 1 "template/inout.hpp"
namespace Nyaan {

template <typename T, typename U>
ostream &operator<<(ostream &os, const pair<T, U> &p) {
	os << p.first << " " << p.second;
	return os;
}
template <typename T, typename U>
istream &operator>>(istream &is, pair<T, U> &p) {
	is >> p.first >> p.second;
	return is;
}

template <typename T>
ostream &operator<<(ostream &os, const vector<T> &v) {
	int s = (int)v.size();
	for(int i = 0; i < s; i++) os << (i ? " " : "") << v[i];
	return os;
}
template <typename T>
istream &operator>>(istream &is, vector<T> &v) {
	for(auto &x : v) is >> x;
	return is;
}

void in() {}
template <typename T, class... U>
void in(T &t, U &...u) {
	cin >> t;
	in(u...);
}

void out() { cout << "\n"; }
template <typename T, class... U, char sep = ' '>
void out(const T &t, const U &...u) {
	cout << t;
	if(sizeof...(u)) cout << sep;
	out(u...);
}

void outr() {}
template <typename T, class... U, char sep = ' '>
void outr(const T &t, const U &...u) {
	cout << t;
	outr(u...);
}

struct IoSetupNya {
	IoSetupNya() {
		cin.tie(nullptr);
		ios::sync_with_stdio(false);
		cout << fixed << setprecision(15);
		cerr << fixed << setprecision(7);
	}
} iosetupnya;

}  // namespace Nyaan
#line 64 "template/template.hpp"

// debug
#line 1 "template/debug.hpp"
namespace DebugImpl {

template <typename U, typename = void>
struct is_specialize : false_type {};
template <typename U>
struct is_specialize<
    U, typename conditional<false, typename U::iterator, void>::type>
  : true_type {};
template <typename U>
struct is_specialize<
    U, typename conditional<false, decltype(U::first), void>::type>
  : true_type {};
template <typename U>
struct is_specialize<U, enable_if_t<is_integral<U>::value, void>> : true_type {
};

void dump(const char &t) { cerr << t; }

void dump(const string &t) { cerr << t; }

void dump(const bool &t) { cerr << (t ? "true" : "false"); }

template <typename U,
          enable_if_t<!is_specialize<U>::value, nullptr_t> = nullptr>
void dump(const U &t) {
	cerr << t;
}

template <typename T>
void dump(const T &t, enable_if_t<is_integral<T>::value> * = nullptr) {
	string res;
	if(t == Nyaan::inf) res = "inf";
	if constexpr(is_signed<T>::value) {
		if(t == -Nyaan::inf) res = "-inf";
	}
	if constexpr(sizeof(T) == 8) {
		if(t == Nyaan::infLL) res = "inf";
		if constexpr(is_signed<T>::value) {
			if(t == -Nyaan::infLL) res = "-inf";
		}
	}
	if(res.empty()) res = to_string(t);
	cerr << res;
}

template <typename T, typename U>
void dump(const pair<T, U> &);
template <typename T>
void dump(const pair<T *, int> &);

template <typename T>
void dump(const T &t,
          enable_if_t<!is_void<typename T::iterator>::value> * = nullptr) {
	cerr << "[ ";
	for(auto it = t.begin(); it != t.end();) {
		dump(*it);
		cerr << (++it == t.end() ? "" : ", ");
	}
	cerr << " ]";
}

template <typename T, typename U>
void dump(const pair<T, U> &t) {
	cerr << "( ";
	dump(t.first);
	cerr << ", ";
	dump(t.second);
	cerr << " )";
}

template <typename T>
void dump(const pair<T *, int> &t) {
	cerr << "[ ";
	for(int i = 0; i < t.second; i++) {
		dump(t.first[i]);
		cerr << (i == t.second - 1 ? "" : ", ");
	}
	cerr << " ]";
}

void trace() { cerr << endl; }
template <typename Head, typename... Tail>
void trace(Head &&head, Tail &&...tail) {
	cerr << " ";
	dump(head);
	if(sizeof...(tail) != 0) cerr << ",";
	trace(forward<Tail>(tail)...);
}

}  // namespace DebugImpl

#ifdef NyaanDebug
#define trc(...)                                \
	do {                                        \
		cerr << "## " << #__VA_ARGS__ << " = "; \
		DebugImpl::trace(__VA_ARGS__);          \
	} while(0)
#else
#define trc(...) (void(0))
#endif
#line 67 "template/template.hpp"

// macro
#line 1 "template/macro.hpp"
#define each(x, v) for(auto &&x : v)
#define each2(x, y, v) for(auto &&[x, y] : v)
#define all(v) (v).begin(), (v).end()
#define rep(i, N) for(long long i = 0; i < (long long)(N); i++)
#define repr(i, N) for(long long i = (long long)(N)-1; i >= 0; i--)
#define rep1(i, N) for(long long i = 1; i <= (long long)(N); i++)
#define repr1(i, N) for(long long i = (N); (long long)(i) > 0; i--)
#define reg(i, a, b) for(long long i = (a); i < (b); i++)
#define regr(i, a, b) for(long long i = (b)-1; i >= (a); i--)
#define fi first
#define se second
#define ini(...)     \
	int __VA_ARGS__; \
	in(__VA_ARGS__)
#define inl(...)           \
	long long __VA_ARGS__; \
	in(__VA_ARGS__)
#define ins(...)        \
	string __VA_ARGS__; \
	in(__VA_ARGS__)
#define in2(s, t)                            \
	for(int i = 0; i < (int)s.size(); i++) { \
		in(s[i], t[i]);                      \
	}
#define in3(s, t, u)                         \
	for(int i = 0; i < (int)s.size(); i++) { \
		in(s[i], t[i], u[i]);                \
	}
#define in4(s, t, u, v)                      \
	for(int i = 0; i < (int)s.size(); i++) { \
		in(s[i], t[i], u[i], v[i]);          \
	}
#define die(...)                 \
	do {                         \
		Nyaan::out(__VA_ARGS__); \
		return;                  \
	} while(0)
#line 70 "template/template.hpp"

namespace Nyaan {
void solve();
}
#line 2 "data-structure/hash-map-variable-length.hpp"

template <typename Key, typename Val>
struct HashMap {
	using u32 = uint32_t;
	using u64 = uint64_t;

	u32 cap, s;
	vector<Key> keys;
	vector<Val> vals;
	vector<bool> flag;
	u64 r;
	u32 shift;
	Val DefaultValue;

	static u64 rng() {
		u64 m = chrono::duration_cast<chrono::nanoseconds>(
		            chrono::high_resolution_clock::now().time_since_epoch())
		            .count();
		m ^= m >> 16;
		m ^= m << 32;
		return m;
	}

	void reallocate() {
		cap <<= 1;
		vector<Key> k(cap);
		vector<Val> v(cap);
		vector<bool> f(cap);
		u32 sh = shift - 1;
		for(int i = 0; i < (int)flag.size(); i++) {
			if(flag[i]) {
				u32 hash = (u64(keys[i]) * r) >> sh;
				while(f[hash]) hash = (hash + 1) & (cap - 1);
				k[hash] = keys[i];
				v[hash] = vals[i];
				f[hash] = 1;
			}
		}
		keys.swap(k);
		vals.swap(v);
		flag.swap(f);
		--shift;
	}

	explicit HashMap()
	  : cap(8),
	    s(0),
	    keys(cap),
	    vals(cap),
	    flag(cap),
	    r(rng()),
	    shift(64 - __lg(cap)),
	    DefaultValue(Val()) {}

	Val &operator[](const Key &i) {
		u32 hash = (u64(i) * r) >> shift;
		while(true) {
			if(!flag[hash]) {
				if(s + s / 4 >= cap) {
					reallocate();
					return (*this)[i];
				}
				keys[hash] = i;
				flag[hash] = 1;
				++s;
				return vals[hash] = DefaultValue;
			}
			if(keys[hash] == i) return vals[hash];
			hash = (hash + 1) & (cap - 1);
		}
	}

	// exist -> return pointer of Val
	// not exist -> return nullptr
	const Val *find(const Key &i) const {
		u32 hash = (u64(i) * r) >> shift;
		while(true) {
			if(!flag[hash]) return nullptr;
			if(keys[hash] == i) return &(vals[hash]);
			hash = (hash + 1) & (cap - 1);
		}
	}

	// return vector< pair<const Key&, val& > >
	vector<pair<Key, Val>> enumerate() const {
		vector<pair<Key, Val>> ret;
		for(u32 i = 0; i < cap; ++i)
			if(flag[i]) ret.emplace_back(keys[i], vals[i]);
		return ret;
	}

	int size() const { return s; }

	// set default_value
	void set_default(const Val &val) { DefaultValue = val; }
};

/**
 * @brief Hash Map(可変長版)
 * @docs docs/data-structure/hash-map.md
 */
#line 2 "data-structure-2d/dynamic-binary-indexed-tree-2d.hpp"

#line 2 "data-structure/dynamic-binary-indexed-tree.hpp"

#line 4 "data-structure/dynamic-binary-indexed-tree.hpp"

template <typename S, typename T>
struct DynamicFenwickTree {
	S N;
	HashMap<S, T> data;
	explicit DynamicFenwickTree() = default;
	explicit DynamicFenwickTree(S size) { N = size + 1; }

	void add(S k, T x) {
		for(++k; k < N; k += k & -k) data[k] += x;
	}

	// [0, k)
	T sum(S k) const {
		if(k < 0) return 0;
		T ret = T();
		for(; k > 0; k -= k & -k) {
			const T *p = data.find(k);
			ret += p ? *p : T();
		}
		return ret;
	}

	// [a, b)
	T sum(S a, S b) const { return sum(b) - sum(a); }

	T operator[](S k) const { return sum(k + 1) - sum(k); }

	S lower_bound(T w) {
		if(w <= 0) return 0;
		S x = 0;
		for(S k = 1 << __lg(N); k; k >>= 1) {
			if(x + k <= N - 1 && data[x + k] < w) {
				w -= data[x + k];
				x += k;
			}
		}
		return x;
	}
};

/**
 * @brief 動的Binary Indexed Tree
 * @docs docs/data-structure/dynamic-binary-indexed-tree.md
 */
#line 4 "data-structure-2d/dynamic-binary-indexed-tree-2d.hpp"

template <typename T>
struct DynamicFenwickTree2D {
	using BIT = DynamicFenwickTree<int, T>;
	int N, M;
	vector<BIT *> bit;
	DynamicFenwickTree2D() = default;
	DynamicFenwickTree2D(int n, int m) : N(n + 1), M(m) {
		for(int _ = 0; _ < N; ++_) bit.push_back(new BIT(M));
	}

	void add(int i, int j, const T &x) {
		for(++i; i < N; i += i & -i) (*bit[i]).add(j, x);
	}

	// i = [0, n), j = [0, m)
	T sum(int n, int m) const {
		if(n < 0 || m < 0) return T();
		T ret = T();
		for(; n; n -= n & -n) ret += (*bit[n]).sum(m);
		return ret;
	}

	// i = [nl, nr), j = [ml, mr)
	T sum(int nl, int ml, int nr, int mr) const {
		T ret = T();
		while(nl != nr) {
			if(nl < nr) {
				ret += (*bit[nr]).sum(ml, mr);
				nr -= nr & -nr;
			} else {
				ret -= (*bit[nl]).sum(ml, mr);
				nl -= nl & -nl;
			}
		}
		return ret;
	}
};

/*
 * @brief 動的二次元Binary Indexed Tree
 */
#line 2 "misc/compress.hpp"

template <class T>
struct compress {
	vector<T> xs;
	compress(const vector<T> &v) {
		xs.reserve(v.size());
		for(T x : v) xs.push_back(x);
		sort(xs.begin(), xs.end());
		xs.erase(unique(xs.begin(), xs.end()), xs.end());
	}
	int get(const T &x) const {
		return lower_bound(xs.begin(), xs.end(), x) - xs.begin();
	}
	inline int operator()(const T &x) const { return get(x); }
	T operator[](int i) { return xs[i]; }
	int size() const { return xs.size(); }
};

/**
 * 座標圧縮
 */
#line 2 "misc/fastio.hpp"

#line 6 "misc/fastio.hpp"

using namespace std;

namespace fastio {
static constexpr int SZ = 1 << 17;
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;

inline 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;
}

inline void flush() {
	fwrite(outbuf, 1, out_right, stdout);
	out_right = 0;
}

inline void skip_space() {
	if(in_left + 32 > in_right) load();
	while(inbuf[in_left] <= ' ') in_left++;
}

inline void rd(char &c) {
	if(in_left + 32 > in_right) load();
	c = inbuf[in_left++];
}
template <typename T>
inline void rd(T &x) {
	if(in_left + 32 > in_right) load();
	char c;
	do c = inbuf[in_left++];
	while(c < '-');
	[[maybe_unused]] bool minus = false;
	if constexpr(is_signed<T>::value == true) {
		if(c == '-') minus = true, c = inbuf[in_left++];
	}
	x = 0;
	while(c >= '0') {
		x = x * 10 + (c & 15);
		c = inbuf[in_left++];
	}
	if constexpr(is_signed<T>::value == true) {
		if(minus) x = -x;
	}
}
inline void rd() {}
template <typename Head, typename... Tail>
inline void rd(Head &head, Tail &...tail) {
	rd(head);
	rd(tail...);
}

inline void wt(char c) {
	if(out_right > SZ - 32) flush();
	outbuf[out_right++] = c;
}
inline void wt(bool b) {
	if(out_right > SZ - 32) flush();
	outbuf[out_right++] = b ? '1' : '0';
}
inline void wt(const string &s) {
	if(out_right + s.size() > SZ - 32) flush();
	memcpy(outbuf + out_right, s.data(), sizeof(char) * s.size());
	out_right += s.size();
}
template <typename T>
inline void wt(T x) {
	if(out_right > SZ - 32) flush();
	if(!x) {
		outbuf[out_right++] = '0';
		return;
	}
	if constexpr(is_signed<T>::value == true) {
		if(x < 0) outbuf[out_right++] = '-', x = -x;
	}
	int i = 12;
	char buf[16];
	while(x >= 10000) {
		memcpy(buf + i, pre.num + (x % 10000) * 4, 4);
		x /= 10000;
		i -= 4;
	}
	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 + 4, 12 - i);
	out_right += 12 - i;
}
inline void wt() {}
template <typename Head, typename... Tail>
inline void wt(Head &&head, Tail &&...tail) {
	wt(head);
	wt(forward<Tail>(tail)...);
}
template <typename... Args>
inline void wtn(Args &&...x) {
	wt(forward<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 8 "verify/verify-yosupo-ds/yosupo-point-add-rectangle-sum-bit2d.test.cpp"

#line 1 "/Users/nok0/Documents/Programming/nok0/atcoder/modint.hpp"



#line 6 "/Users/nok0/Documents/Programming/nok0/atcoder/modint.hpp"
#include <type_traits>

#ifdef _MSC_VER
#include <intrin.h>
#endif

#line 1 "/Users/nok0/Documents/Programming/nok0/atcoder/internal_math.hpp"



#line 5 "/Users/nok0/Documents/Programming/nok0/atcoder/internal_math.hpp"

#ifdef _MSC_VER
#include <intrin.h>
#endif

namespace atcoder {

namespace internal {

// @param m `1 <= m`
// @return x mod m
constexpr long long safe_mod(long long x, long long m) {
    x %= m;
    if (x < 0) x += m;
    return x;
}

// Fast modular multiplication by barrett reduction
// Reference: https://en.wikipedia.org/wiki/Barrett_reduction
// NOTE: reconsider after Ice Lake
struct barrett {
    unsigned int _m;
    unsigned long long im;

    // @param m `1 <= m < 2^31`
    explicit barrett(unsigned int m) : _m(m), im((unsigned long long)(-1) / m + 1) {}

    // @return m
    unsigned int umod() const { return _m; }

    // @param a `0 <= a < m`
    // @param b `0 <= b < m`
    // @return `a * b % m`
    unsigned int mul(unsigned int a, unsigned int b) const {
        // [1] m = 1
        // a = b = im = 0, so okay

        // [2] m >= 2
        // im = ceil(2^64 / m)
        // -> im * m = 2^64 + r (0 <= r < m)
        // let z = a*b = c*m + d (0 <= c, d < m)
        // a*b * im = (c*m + d) * im = c*(im*m) + d*im = c*2^64 + c*r + d*im
        // c*r + d*im < m * m + m * im < m * m + 2^64 + m <= 2^64 + m * (m + 1) < 2^64 * 2
        // ((ab * im) >> 64) == c or c + 1
        unsigned long long z = a;
        z *= b;
#ifdef _MSC_VER
        unsigned long long x;
        _umul128(z, im, &x);
#else
        unsigned long long x =
            (unsigned long long)(((unsigned __int128)(z)*im) >> 64);
#endif
        unsigned int v = (unsigned int)(z - x * _m);
        if (_m <= v) v += _m;
        return v;
    }
};

// @param n `0 <= n`
// @param m `1 <= m`
// @return `(x ** n) % m`
constexpr long long pow_mod_constexpr(long long x, long long n, int m) {
    if (m == 1) return 0;
    unsigned int _m = (unsigned int)(m);
    unsigned long long r = 1;
    unsigned long long y = safe_mod(x, m);
    while (n) {
        if (n & 1) r = (r * y) % _m;
        y = (y * y) % _m;
        n >>= 1;
    }
    return r;
}

// Reference:
// M. Forisek and J. Jancina,
// Fast Primality Testing for Integers That Fit into a Machine Word
// @param n `0 <= n`
constexpr bool is_prime_constexpr(int n) {
    if (n <= 1) return false;
    if (n == 2 || n == 7 || n == 61) return true;
    if (n % 2 == 0) return false;
    long long d = n - 1;
    while (d % 2 == 0) d /= 2;
    constexpr long long bases[3] = {2, 7, 61};
    for (long long a : bases) {
        long long t = d;
        long long y = pow_mod_constexpr(a, t, n);
        while (t != n - 1 && y != 1 && y != n - 1) {
            y = y * y % n;
            t <<= 1;
        }
        if (y != n - 1 && t % 2 == 0) {
            return false;
        }
    }
    return true;
}
template <int n> constexpr bool is_prime = is_prime_constexpr(n);

// @param b `1 <= b`
// @return pair(g, x) s.t. g = gcd(a, b), xa = g (mod b), 0 <= x < b/g
constexpr std::pair<long long, long long> inv_gcd(long long a, long long b) {
    a = safe_mod(a, b);
    if (a == 0) return {b, 0};

    // Contracts:
    // [1] s - m0 * a = 0 (mod b)
    // [2] t - m1 * a = 0 (mod b)
    // [3] s * |m1| + t * |m0| <= b
    long long s = b, t = a;
    long long m0 = 0, m1 = 1;

    while (t) {
        long long u = s / t;
        s -= t * u;
        m0 -= m1 * u;  // |m1 * u| <= |m1| * s <= b

        // [3]:
        // (s - t * u) * |m1| + t * |m0 - m1 * u|
        // <= s * |m1| - t * u * |m1| + t * (|m0| + |m1| * u)
        // = s * |m1| + t * |m0| <= b

        auto tmp = s;
        s = t;
        t = tmp;
        tmp = m0;
        m0 = m1;
        m1 = tmp;
    }
    // by [3]: |m0| <= b/g
    // by g != b: |m0| < b/g
    if (m0 < 0) m0 += b / s;
    return {s, m0};
}

// Compile time primitive root
// @param m must be prime
// @return primitive root (and minimum in now)
constexpr int primitive_root_constexpr(int m) {
    if (m == 2) return 1;
    if (m == 167772161) return 3;
    if (m == 469762049) return 3;
    if (m == 754974721) return 11;
    if (m == 998244353) return 3;
    int divs[20] = {};
    divs[0] = 2;
    int cnt = 1;
    int x = (m - 1) / 2;
    while (x % 2 == 0) x /= 2;
    for (int i = 3; (long long)(i)*i <= x; i += 2) {
        if (x % i == 0) {
            divs[cnt++] = i;
            while (x % i == 0) {
                x /= i;
            }
        }
    }
    if (x > 1) {
        divs[cnt++] = x;
    }
    for (int g = 2;; g++) {
        bool ok = true;
        for (int i = 0; i < cnt; i++) {
            if (pow_mod_constexpr(g, (m - 1) / divs[i], m) == 1) {
                ok = false;
                break;
            }
        }
        if (ok) return g;
    }
}
template <int m> constexpr int primitive_root = primitive_root_constexpr(m);

// @param n `n < 2^32`
// @param m `1 <= m < 2^32`
// @return sum_{i=0}^{n-1} floor((ai + b) / m) (mod 2^64)
unsigned long long floor_sum_unsigned(unsigned long long n,
                                      unsigned long long m,
                                      unsigned long long a,
                                      unsigned long long b) {
    unsigned long long ans = 0;
    while (true) {
        if (a >= m) {
            ans += n * (n - 1) / 2 * (a / m);
            a %= m;
        }
        if (b >= m) {
            ans += n * (b / m);
            b %= m;
        }

        unsigned long long y_max = a * n + b;
        if (y_max < m) break;
        // y_max < m * (n + 1)
        // floor(y_max / m) <= n
        n = (unsigned long long)(y_max / m);
        b = (unsigned long long)(y_max % m);
        std::swap(m, a);
    }
    return ans;
}

}  // namespace internal

}  // namespace atcoder


#line 1 "/Users/nok0/Documents/Programming/nok0/atcoder/internal_type_traits.hpp"



#line 7 "/Users/nok0/Documents/Programming/nok0/atcoder/internal_type_traits.hpp"

namespace atcoder {

namespace internal {

#ifndef _MSC_VER
template <class T>
using is_signed_int128 =
    typename std::conditional<std::is_same<T, __int128_t>::value ||
                                  std::is_same<T, __int128>::value,
                              std::true_type,
                              std::false_type>::type;

template <class T>
using is_unsigned_int128 =
    typename std::conditional<std::is_same<T, __uint128_t>::value ||
                                  std::is_same<T, unsigned __int128>::value,
                              std::true_type,
                              std::false_type>::type;

template <class T>
using make_unsigned_int128 =
    typename std::conditional<std::is_same<T, __int128_t>::value,
                              __uint128_t,
                              unsigned __int128>;

template <class T>
using is_integral = typename std::conditional<std::is_integral<T>::value ||
                                                  is_signed_int128<T>::value ||
                                                  is_unsigned_int128<T>::value,
                                              std::true_type,
                                              std::false_type>::type;

template <class T>
using is_signed_int = typename std::conditional<(is_integral<T>::value &&
                                                 std::is_signed<T>::value) ||
                                                    is_signed_int128<T>::value,
                                                std::true_type,
                                                std::false_type>::type;

template <class T>
using is_unsigned_int =
    typename std::conditional<(is_integral<T>::value &&
                               std::is_unsigned<T>::value) ||
                                  is_unsigned_int128<T>::value,
                              std::true_type,
                              std::false_type>::type;

template <class T>
using to_unsigned = typename std::conditional<
    is_signed_int128<T>::value,
    make_unsigned_int128<T>,
    typename std::conditional<std::is_signed<T>::value,
                              std::make_unsigned<T>,
                              std::common_type<T>>::type>::type;

#else

template <class T> using is_integral = typename std::is_integral<T>;

template <class T>
using is_signed_int =
    typename std::conditional<is_integral<T>::value && std::is_signed<T>::value,
                              std::true_type,
                              std::false_type>::type;

template <class T>
using is_unsigned_int =
    typename std::conditional<is_integral<T>::value &&
                                  std::is_unsigned<T>::value,
                              std::true_type,
                              std::false_type>::type;

template <class T>
using to_unsigned = typename std::conditional<is_signed_int<T>::value,
                                              std::make_unsigned<T>,
                                              std::common_type<T>>::type;

#endif

template <class T>
using is_signed_int_t = std::enable_if_t<is_signed_int<T>::value>;

template <class T>
using is_unsigned_int_t = std::enable_if_t<is_unsigned_int<T>::value>;

template <class T> using to_unsigned_t = typename to_unsigned<T>::type;

}  // namespace internal

}  // namespace atcoder


#line 14 "/Users/nok0/Documents/Programming/nok0/atcoder/modint.hpp"

namespace atcoder {

namespace internal {

struct modint_base {};
struct static_modint_base : modint_base {};

template <class T> using is_modint = std::is_base_of<modint_base, T>;
template <class T> using is_modint_t = std::enable_if_t<is_modint<T>::value>;

}  // namespace internal

template <int m, std::enable_if_t<(1 <= m)>* = nullptr>
struct static_modint : internal::static_modint_base {
    using mint = static_modint;

  public:
    static constexpr int mod() { return m; }
    static mint raw(int v) {
        mint x;
        x._v = v;
        return x;
    }

    static_modint() : _v(0) {}
    template <class T, internal::is_signed_int_t<T>* = nullptr>
    static_modint(T v) {
        long long x = (long long)(v % (long long)(umod()));
        if (x < 0) x += umod();
        _v = (unsigned int)(x);
    }
    template <class T, internal::is_unsigned_int_t<T>* = nullptr>
    static_modint(T v) {
        _v = (unsigned int)(v % umod());
    }

    unsigned int val() const { return _v; }

    mint& operator++() {
        _v++;
        if (_v == umod()) _v = 0;
        return *this;
    }
    mint& operator--() {
        if (_v == 0) _v = umod();
        _v--;
        return *this;
    }
    mint operator++(int) {
        mint result = *this;
        ++*this;
        return result;
    }
    mint operator--(int) {
        mint result = *this;
        --*this;
        return result;
    }

    mint& operator+=(const mint& rhs) {
        _v += rhs._v;
        if (_v >= umod()) _v -= umod();
        return *this;
    }
    mint& operator-=(const mint& rhs) {
        _v -= rhs._v;
        if (_v >= umod()) _v += umod();
        return *this;
    }
    mint& operator*=(const mint& rhs) {
        unsigned long long z = _v;
        z *= rhs._v;
        _v = (unsigned int)(z % umod());
        return *this;
    }
    mint& operator/=(const mint& rhs) { return *this = *this * rhs.inv(); }

    mint operator+() const { return *this; }
    mint operator-() const { return mint() - *this; }

    mint pow(long long n) const {
        assert(0 <= n);
        mint x = *this, r = 1;
        while (n) {
            if (n & 1) r *= x;
            x *= x;
            n >>= 1;
        }
        return r;
    }
    mint inv() const {
        if (prime) {
            assert(_v);
            return pow(umod() - 2);
        } else {
            auto eg = internal::inv_gcd(_v, m);
            assert(eg.first == 1);
            return eg.second;
        }
    }

    friend mint operator+(const mint& lhs, const mint& rhs) {
        return mint(lhs) += rhs;
    }
    friend mint operator-(const mint& lhs, const mint& rhs) {
        return mint(lhs) -= rhs;
    }
    friend mint operator*(const mint& lhs, const mint& rhs) {
        return mint(lhs) *= rhs;
    }
    friend mint operator/(const mint& lhs, const mint& rhs) {
        return mint(lhs) /= rhs;
    }
    friend bool operator==(const mint& lhs, const mint& rhs) {
        return lhs._v == rhs._v;
    }
    friend bool operator!=(const mint& lhs, const mint& rhs) {
        return lhs._v != rhs._v;
    }

  private:
    unsigned int _v;
    static constexpr unsigned int umod() { return m; }
    static constexpr bool prime = internal::is_prime<m>;
};

template <int id> struct dynamic_modint : internal::modint_base {
    using mint = dynamic_modint;

  public:
    static int mod() { return (int)(bt.umod()); }
    static void set_mod(int m) {
        assert(1 <= m);
        bt = internal::barrett(m);
    }
    static mint raw(int v) {
        mint x;
        x._v = v;
        return x;
    }

    dynamic_modint() : _v(0) {}
    template <class T, internal::is_signed_int_t<T>* = nullptr>
    dynamic_modint(T v) {
        long long x = (long long)(v % (long long)(mod()));
        if (x < 0) x += mod();
        _v = (unsigned int)(x);
    }
    template <class T, internal::is_unsigned_int_t<T>* = nullptr>
    dynamic_modint(T v) {
        _v = (unsigned int)(v % mod());
    }

    unsigned int val() const { return _v; }

    mint& operator++() {
        _v++;
        if (_v == umod()) _v = 0;
        return *this;
    }
    mint& operator--() {
        if (_v == 0) _v = umod();
        _v--;
        return *this;
    }
    mint operator++(int) {
        mint result = *this;
        ++*this;
        return result;
    }
    mint operator--(int) {
        mint result = *this;
        --*this;
        return result;
    }

    mint& operator+=(const mint& rhs) {
        _v += rhs._v;
        if (_v >= umod()) _v -= umod();
        return *this;
    }
    mint& operator-=(const mint& rhs) {
        _v += mod() - rhs._v;
        if (_v >= umod()) _v -= umod();
        return *this;
    }
    mint& operator*=(const mint& rhs) {
        _v = bt.mul(_v, rhs._v);
        return *this;
    }
    mint& operator/=(const mint& rhs) { return *this = *this * rhs.inv(); }

    mint operator+() const { return *this; }
    mint operator-() const { return mint() - *this; }

    mint pow(long long n) const {
        assert(0 <= n);
        mint x = *this, r = 1;
        while (n) {
            if (n & 1) r *= x;
            x *= x;
            n >>= 1;
        }
        return r;
    }
    mint inv() const {
        auto eg = internal::inv_gcd(_v, mod());
        assert(eg.first == 1);
        return eg.second;
    }

    friend mint operator+(const mint& lhs, const mint& rhs) {
        return mint(lhs) += rhs;
    }
    friend mint operator-(const mint& lhs, const mint& rhs) {
        return mint(lhs) -= rhs;
    }
    friend mint operator*(const mint& lhs, const mint& rhs) {
        return mint(lhs) *= rhs;
    }
    friend mint operator/(const mint& lhs, const mint& rhs) {
        return mint(lhs) /= rhs;
    }
    friend bool operator==(const mint& lhs, const mint& rhs) {
        return lhs._v == rhs._v;
    }
    friend bool operator!=(const mint& lhs, const mint& rhs) {
        return lhs._v != rhs._v;
    }

  private:
    unsigned int _v;
    static internal::barrett bt;
    static unsigned int umod() { return bt.umod(); }
};
template <int id> internal::barrett dynamic_modint<id>::bt(998244353);

using modint998244353 = static_modint<998244353>;
using modint1000000007 = static_modint<1000000007>;
using modint = dynamic_modint<-1>;

namespace internal {

template <class T>
using is_static_modint = std::is_base_of<internal::static_modint_base, T>;

template <class T>
using is_static_modint_t = std::enable_if_t<is_static_modint<T>::value>;

template <class> struct is_dynamic_modint : public std::false_type {};
template <int id>
struct is_dynamic_modint<dynamic_modint<id>> : public std::true_type {};

template <class T>
using is_dynamic_modint_t = std::enable_if_t<is_dynamic_modint<T>::value>;

}  // namespace internal

}  // namespace atcoder


#line 4 "/Users/nok0/Documents/Programming/nok0/math/factorial.hpp"

#line 6 "/Users/nok0/Documents/Programming/nok0/math/factorial.hpp"

template <class T>
struct factorial {
public:
	static int MAX;
	static std::vector<T> fac, finv, inv;

	factorial() {}

	T binom(int n, int r) {
		if(n < r or n < 0 or r < 0) return T(0);
		assert(n < MAX);
		return fac[n] * finv[r] * finv[n - r];
	}

	T large_binom(int n, int r) {
		if(n < r or n < 0 or r < 0) return T(0);
		assert(r < MAX);
		T ret = finv[r];
		for(int i = 1; i <= r; ++i)
			ret *= (n + 1 - i);
		return ret;
	}

	static void set_size(int n = 3000000) {
		MAX = (n > 1 ? n : 1) + 1;
		if((int)fac.size() >= MAX) return;
		fac.resize(MAX);
		finv.resize(MAX);
		inv.resize(MAX);
		const int MOD = T::mod();
		fac[0] = fac[1] = 1;
		finv[0] = finv[1] = 1;
		inv[1] = 1;
		for(int i = 2; i < MAX; i++) {
			fac[i] = fac[i - 1] * i;
			inv[i] = (T)MOD - inv[MOD % i] * (MOD / i);
			finv[i] = finv[i - 1] * inv[i];
		}
	}
};
template <class T>
int factorial<T>::MAX = 0;
template <class T>
std::vector<T> factorial<T>::fac;
template <class T>
std::vector<T> factorial<T>::finv;
template <class T>
std::vector<T> factorial<T>::inv;
#line 3 "/Users/nok0/Documents/Programming/nok0/math/modint_iostream.hpp"

#line 5 "/Users/nok0/Documents/Programming/nok0/math/modint_iostream.hpp"
template <int m>
std::istream &std::operator>>(std::istream &is, atcoder::static_modint<m> &a) {
	long long v;
	is >> v;
	a = v;
	return is;
}
template <int m>
std::istream &std::operator>>(std::istream &is, atcoder::dynamic_modint<m> &a) {
	long long v;
	is >> v;
	a = v;
	return is;
}
template <int m>
std::ostream &std::operator<<(std::ostream &os, const atcoder::static_modint<m> &a) { return os << a.val(); }
template <int m>
std::ostream &std::operator<<(std::ostream &os, const atcoder::dynamic_modint<m> &a) { return os << a.val(); }
#line 742 "e.cpp"

using mint = atcoder::modint998244353;

void main_() {
	INT(n);
	VEC(pii, xy, n);
	V<> x, y;
	foa(p, xy) {
		x.pb(p.first);
		y.pb(p.second);
	}
	auto rx = press(x), ry = press(y);
	foa(p, xy) {
		p.first = lb(rx, p.first);
		p.second = lb(ry, p.second);
	}
	DynamicFenwickTree2D<mint> bt(n, n);
	debug(xy);
	auto [sx, sy] = xy[0];
	auto [gx, gy] = xy[n - 1];
	bt.add(sx, sy, 1);
	vector<mint> add(n);
	REP(i, 1, n) {
		auto [x, y] = xy[i];
		mint val;
		if(sx < gx) {
			if(sy < gy) {
				val = bt.sum(sx, sy, x + 1, y + 1);
			} else if(sy == gy) {
				val = bt.sum(sx, sy, x + 1, sy + 1);
			} else {
				debug(sx, y, x + 1, sy + 1);
				val = bt.sum(sx, y, x + 1, sy + 1);
				debug(val);
			}
		} else if(sx == gx) {
			if(sy < gy) {
				val = bt.sum(sx, sy, sx + 1, y + 1);
			} else {
				val = bt.sum(sx, y, sx + 1, sy + 1);
			}
		} else {
			if(sy < gy) {
				val = bt.sum(x, sy, sx + 1, y + 1);
			} else if(sy == gy) {
				val = bt.sum(x, sy, sx + 1, sy + 1);
			} else {
				val = bt.sum(x, y, sx + 1, sy + 1);
			}
		}
		add[i] = val;
		bt.add(x, y, val);
	}
	REP(i, n) {
		debug(xy[i]);
		debug(add[i]);
	}
	debug(xy);
	debug(add);
	print(bt.sum(gx, gy, gx + 1, gy + 1));
}
0