#line 2 "library/template/template.hpp" #include using namespace std; #line 2 "library/template/macro.hpp" #define rep(i, a, b) for (int i = (a); i < (int)(b); i++) #define rrep(i, a, b) for (int i = (int)(b) - 1; i >= (a); i--) #define ALL(v) (v).begin(), (v).end() #define UNIQUE(v) sort(ALL(v)), (v).erase(unique(ALL(v)), (v).end()) #define SZ(v) (int)v.size() #define MIN(v) *min_element(ALL(v)) #define MAX(v) *max_element(ALL(v)) #define LB(v, x) int(lower_bound(ALL(v), (x)) - (v).begin()) #define UB(v, x) int(upper_bound(ALL(v), (x)) - (v).begin()) #define YN(b) cout << ((b) ? "YES" : "NO") << "\n"; #define Yn(b) cout << ((b) ? "Yes" : "No") << "\n"; #define yn(b) cout << ((b) ? "yes" : "no") << "\n"; #line 6 "library/template/template.hpp" #line 2 "library/template/util.hpp" using uint = unsigned int; using ll = long long int; using ull = unsigned long long; using i128 = __int128_t; using u128 = __uint128_t; template S SUM(const vector &a) { return accumulate(ALL(a), S(0)); } template inline bool chmin(T &a, T b) { if (a > b) { a = b; return true; } return false; } template inline bool chmax(T &a, T b) { if (a < b) { a = b; return true; } return false; } template int popcnt(T x) { return __builtin_popcountll(x); } template int topbit(T x) { return (x == 0 ? -1 : 63 - __builtin_clzll(x)); } template int lowbit(T x) { return (x == 0 ? -1 : __builtin_ctzll(x)); } #line 8 "library/template/template.hpp" #line 2 "library/template/inout.hpp" struct Fast { Fast() { cin.tie(nullptr); ios_base::sync_with_stdio(false); cout << fixed << setprecision(15); } } fast; istream& operator>>(istream& is, __uint128_t& x) { string s; is >> s; x = 0; for (auto c : s) x = x * 10 + (c - '0'); return is; } ostream& operator<<(ostream& os, const __uint128_t& x) { int buf[39]; buf[0] = 0; int k = x == 0; for (auto y = x; y > 0; y /= 10) buf[k++] = int(y % 10); while (k > 0) os << buf[--k]; return os; } istream& operator>>(istream& is, __int128_t& x) { string s; is >> s; auto it = s.begin(); bool nega = *it == '-'; if (nega) it++; x = 0; for (; it < s.end(); it++) x = x * 10 + (*it - '0'); if (nega) x = -x; return is; } ostream& operator<<(ostream& os, const __int128_t& x) { if (x < 0) os << '-'; int buf[39]; buf[0] = 0; int k = x == 0; for (auto y = x < 0 ? -x : x; y > 0; y /= 10) buf[k++] = int(y % 10); while (k > 0) os << buf[--k]; return os; } template istream& operator>>(istream& is, pair& p) { return is >> p.first >> p.second; } template ostream& operator<<(ostream& os, const pair& p) { return os << p.first << " " << p.second; } template istream& operator>>(istream& is, vector& a) { for (auto& v : a) is >> v; return is; } template ostream& operator<<(ostream& os, const vector& a) { for (auto it = a.begin(); it != a.end();) { os << *it; if (++it != a.end()) os << " "; } return os; } template ostream& operator<<(ostream& os, const set& st) { os << "{"; for (auto it = st.begin(); it != st.end();) { os << *it; if (++it != st.end()) os << ","; } os << "}"; return os; } template ostream& operator<<(ostream& os, const map& mp) { os << "{"; for (auto it = mp.begin(); it != mp.end();) { os << it->first << ":" << it->second; if (++it != mp.end()) os << ","; } os << "}"; return os; } void in() {} template void in(T& t, U&... u) { cin >> t; in(u...); } void out() { cout << "\n"; } template void out(const T& t, const U&... u) { cout << t; if (sizeof...(u)) cout << sep; out(u...); } #line 10 "library/template/template.hpp" #line 2 "library/template/debug.hpp" #ifdef LOCAL #define debug 1 #define show(...) _show(0, #__VA_ARGS__, __VA_ARGS__) #else #define debug 0 #define show(...) true #endif template void _show(int i, T name) { cerr << '\n'; } template void _show(int i, const T1 &a, const T2 &b, const T3 &...c) { for (; a[i] != ',' && a[i] != '\0'; i++) cerr << a[i]; cerr << ":" << b << " "; _show(i + 1, a, c...); } #line 2 "main.cpp" #line 2 "library/util/random.hpp" namespace Random { mt19937_64 gen(chrono::steady_clock::now().time_since_epoch().count()); uint64_t get() { return gen(); } template T get(T n) { return get() % n; } template T get(T l, T r) { return get(r - l) % (r - l + 1) + l; } double uniform() { return double(get(1 << 30)) / (1 << 30); } template vector get_vector(size_t n, T l, T r) { vector a(n); for (auto& v : a) v = get(l, r); return a; } template void shuffle(Iter begin, Iter end) { if (begin == end) return; int n = end - begin; for (int i = n - 1; i > 0; i--) { int j = get(i + 1); if (j < i) swap(*(begin + i), *(begin + j)); } } }; // namespace Random /** * @brief Random */ #line 4 "main.cpp" u128 pow(u128 x, int n) { u128 y = 1; while (n) { if (n & 1) y *= x; x *= x; n /= 2; } return y; } u128 sqrt128(u128 n) { u128 l = 0, r = u128(1) << 62; while (r - l > 1) { u128 x = (l + r) / 2; (x * x <= n ? l : r) = x; } return l; } // m <= 2^80 u128 mul(u128 x, u128 y, u128 m) { const int B = 40; const u128 M = (u128(1) << B) - 1; u128 x2 = x >> (B * 2); u128 x1 = (x >> B) & M; u128 x0 = x & M; u128 y2 = y >> (B * 2); u128 y1 = (y >> B) & M; u128 y0 = y & M; u128 z = x2 * y2 % m; z = ((z << B) + x1 * y2 + x2 * y1) % m; z = ((z << B) + x0 * y2 + x1 * y1 + x2 * y0) % m; z = ((z << B) + x0 * y1 + x1 * y0) % m; z = ((z << B) + x0 * y0) % m; return z; } u128 modpow(u128 a, u128 n, u128 p) { a %= p; u128 ret = 1 % p; while (n > 0) { if (n % 2 == 1) ret = mul(ret, a, p); a = mul(a, a, p); n /= 2; } return ret; } u128 gcd(u128 x, u128 y) { while (y != 0) x %= y, swap(x, y); return x; } namespace fast_factorize { bool miller_rabin(const u128& n, vector ws) { if (n <= 2) return n == 2; if (n % 2 == 0) return false; u128 d = n - 1; while (d % 2 == 0) d /= 2; for (auto w : ws) { if (w % n == 0) continue; u128 t = d; u128 y = modpow(w, t, n); while (t != n - 1 && y != 1 && y != n - 1) y = mul(y, y, n), t *= 2; if (y != n - 1 && t % 2 == 0) return false; } return true; } bool miller_rabin_large(u128 n) { return miller_rabin(n, {2, 3, 5, 7, 11, 13, 17, 19, 23, 29, 31, 37, 41}); } bool is_prime(u128 n) { if (n <= 2) return n == 2; if (n % 2 == 0) return false; return miller_rabin_large(n); } u128 pollard_rho(u128 n) { if (~n & 1) return 2; if (is_prime(n)) return n; const int B = 60; const u128 M = (u128(1) << B) - 1; u128 R; auto f = [&](u128 x) -> u128 { return (mul(x, x, n) + R) % n; }; auto rnd_ = [&]() -> u128 { u128 z = (u128(Random::get()) << 64) | u128(Random::get()); return z % (n - 2) + 2; }; int counter = 0; while (1) { u128 x, y, ys, q = 1; R = rnd_(), y = rnd_(); u128 g = 1; constexpr int m = 128; for (int r = 1; g == 1; r <<= 1) { x = y; for (int i = 0; i < r; ++i) y = f(y); for (int k = 0; g == 1 && k < r; k += m) { ys = y; for (int i = 0; i < m && i < r - k; ++i) q = mul(q, x + n - (y = f(y)), n); g = gcd(q, n); } } if (g == n) { do g = gcd(x + n - (ys = f(ys)), n); while (g == 1); } if (g != n) return g; } exit(1); } vector inner_factorize(u128 n) { if (n <= 1) return {}; u128 p = pollard_rho(n); if (p == n) return {u128(p)}; auto l = inner_factorize(p); auto r = inner_factorize(n / p); copy(begin(r), end(r), back_inserter(l)); return l; } vector factorize(u128 n) { auto ret = inner_factorize(n); sort(begin(ret), end(ret)); return ret; } map factor_count(u128 n) { map mp; for (auto& x : factorize(n)) mp[x]++; return mp; } vector divisors(u128 n) { if (n == 0) return {}; vector> v; for (auto& p : factorize(n)) { if (v.empty() || v.back().first != p) { v.emplace_back(p, 1); } else { v.back().second++; } } vector ret; auto f = [&](auto rc, int i, u128 x) -> void { if (i == (int)v.size()) { ret.push_back(x); return; } rc(rc, i + 1, x); for (int j = 0; j < v[i].second; j++) rc(rc, i + 1, x *= v[i].first); }; f(f, 0, 1); sort(begin(ret), end(ret)); return ret; } } // namespace fast_factorize using fast_factorize::divisors; using fast_factorize::factor_count; using fast_factorize::factorize; // https://nyaannyaan.github.io/library/prime/fast-factorize.hpp // https://nyaannyaan.github.io/library/prime/miller-rabin.hpp int main() { u128 n; in(n); vector> ans; for (int e = 1; (u128(1) << e) <= n; e++) { if (e == 1) { // (r-l+1)(l+r)/2=n auto ds = divisors(2 * n); for (auto d : ds) { // r-l+1=d // l+r=2*n/d u128 d1 = 2 * n / d; if ((d & 1) == (d1 & 1)) continue; if (d >= d1) continue; u128 l = (d1 - d + 1) / 2; u128 r = (d1 + d - 1) / 2; ans.push_back({e, l, r}); } sort(ALL(ans)); } else if (e == 2) { // (r-l+1)(2r^2+2lr+2l^2+r-l)=6*n auto ds = divisors(12 * n); // x=l+r,y=r-l // (y+1)(3x^2+y^2+2y)=12*n for (auto d : ds) { if (12 * n / d / d / d == 0) continue; auto y = d - 1; // 3x^2+y^2+2y auto x = y * y + 2 * y; if (x > 12 * n / d) continue; x = 12 * n / d - x; if (x % 3 != 0) continue; x /= 3; auto sq = sqrt128(x); if (sq * sq != x) continue; x = sq; if ((x & 1) != (y & 1)) continue; auto l = (x - y) / 2; auto r = (x + y) / 2; ans.push_back({e, l, r}); } sort(ALL(ans)); } else if (e == 3) { auto ds = divisors(4 * n); for (auto d : ds) { if (d > n / d) continue; // r(r+1)-l(l-1)=d // r(r+1)+l(l-1)=n/d if ((d & 1) != ((n / d) & 1)) continue; auto l1 = (n / d - d) / 2; auto r1 = (n / d + d) / 2; auto l = sqrt128(4 * l1 + 1) / 2; auto r = sqrt128(4 * r1 + 1) / 2; if (l * (l - 1) == l1 && r * (r + 1) == r1) ans.push_back({e, l, r}); } sort(ALL(ans)); } else { map mp; mp[0] = 0; u128 s = 0; for (int x = 1;; x++) { u128 m = n; rep(i, 0, e) m /= x; if (m == 0) break; s += pow(u128(x), e); if (mp.contains(s - n)) { ans.push_back({e, mp[s - n] + 1, x}); } mp[s] = x; } } } out(ans.size()); for (auto [e, l, r] : ans) out(e, l, r); }