結果
問題 | No.1073 無限すごろく |
ユーザー | ngtkana |
提出日時 | 2020-06-06 02:53:16 |
言語 | C++17 (gcc 12.3.0 + boost 1.83.0) |
結果 |
AC
|
実行時間 | 2 ms / 2,000 ms |
コード長 | 7,872 bytes |
コンパイル時間 | 2,370 ms |
コンパイル使用メモリ | 209,584 KB |
実行使用メモリ | 6,944 KB |
最終ジャッジ日時 | 2024-06-01 05:17:09 |
合計ジャッジ時間 | 3,538 ms |
ジャッジサーバーID (参考情報) |
judge2 / judge3 |
(要ログイン)
テストケース
テストケース表示入力 | 結果 | 実行時間 実行使用メモリ |
---|---|---|
testcase_00 | AC | 2 ms
6,816 KB |
testcase_01 | AC | 2 ms
6,816 KB |
testcase_02 | AC | 2 ms
6,944 KB |
testcase_03 | AC | 2 ms
6,944 KB |
testcase_04 | AC | 2 ms
6,944 KB |
testcase_05 | AC | 2 ms
6,940 KB |
testcase_06 | AC | 2 ms
6,940 KB |
testcase_07 | AC | 2 ms
6,940 KB |
testcase_08 | AC | 2 ms
6,944 KB |
testcase_09 | AC | 2 ms
6,940 KB |
testcase_10 | AC | 2 ms
6,940 KB |
testcase_11 | AC | 2 ms
6,944 KB |
testcase_12 | AC | 2 ms
6,944 KB |
testcase_13 | AC | 2 ms
6,944 KB |
testcase_14 | AC | 2 ms
6,940 KB |
testcase_15 | AC | 2 ms
6,940 KB |
testcase_16 | AC | 2 ms
6,940 KB |
testcase_17 | AC | 2 ms
6,940 KB |
testcase_18 | AC | 2 ms
6,940 KB |
testcase_19 | AC | 2 ms
6,940 KB |
testcase_20 | AC | 2 ms
6,940 KB |
testcase_21 | AC | 2 ms
6,940 KB |
testcase_22 | AC | 2 ms
6,940 KB |
testcase_23 | AC | 2 ms
6,940 KB |
testcase_24 | AC | 2 ms
6,944 KB |
testcase_25 | AC | 2 ms
6,944 KB |
testcase_26 | AC | 2 ms
6,940 KB |
testcase_27 | AC | 2 ms
6,940 KB |
testcase_28 | AC | 2 ms
6,944 KB |
testcase_29 | AC | 2 ms
6,940 KB |
testcase_30 | AC | 2 ms
6,944 KB |
testcase_31 | AC | 2 ms
6,940 KB |
testcase_32 | AC | 2 ms
6,940 KB |
ソースコード
#define ENABLE_DEBUG 1 // Kana's kitchen {{{ #include<bits/stdc++.h> #define ALL(v) std::begin(v),std::end(v) #define LOOP(k) for(i64 ngtkana_is_a_genius=0; ngtkana_is_a_genius<(i64)k; ngtkana_is_a_genius++) using i32 = std::int_least32_t; using i64 = std::int_least64_t; using u32 = std::uint_least32_t; using u64 = std::uint_least64_t; using usize = std::size_t; template <class T, class U> using pair = std::pair<U, T>; template <class T> using diag_pair = std::pair<T, T>; template <class... Args> using tuple = std::tuple<Args...>; template <class T> using vec = std::vector<T>; template <class T> using numr = std::numeric_limits<T>; #ifdef NGTKANA #include<debug.hpp> #else #define DEBUG(...)(void)0 #endif /*}}}*/ // mint{{{ template <class ModType> struct modint { using value_type = typename ModType::value_type; using mint = modint<ModType>; using mod_type = ModType; static value_type mod() { return ModType::value; } private: static value_type inverse(value_type x) { value_type y=1,u=mod(),v=0; while(x){ value_type q=u/x; u-=q*x; std::swap(x,u); v-=q*y; std::swap(y,v); } assert(x==0 && std::abs(y)==mod() && std::abs(u)==1 && std::abs(v)<mod()); return v<0?v+mod():v; } public: // the member variable value_type value; // constructors modint()=default; modint(modint const&)=default; modint(modint&&)=default; modint& operator=(modint const&)=default; modint& operator=(modint&&)=default; ~modint()=default; template <class T> modint(T t) : value([t] () mutable { if ( t <= -static_cast<T>(mod()) || static_cast<T>(mod()) <= t ) t %= mod(); return t < 0 ? t + mod() : t; }()) {} // operators mint& operator+= (mint y) { value += y.value; if (mod() <= value) value -= mod(); return *this; } mint& operator-= (mint y) { value -= y.value; if ( value < 0 ) value += mod(); return *this; } mint& operator*= (mint y) { value = (long long)value * y.value % mod(); return *this; } mint& operator/= (mint y) { value = (long long)value * inverse(y.value) % mod(); return *this; } mint& operator++() { return *this+=1; } mint& operator--() { return *this-=1; } mint operator++(int) const { mint this_=*this; ++*this; return this_; } mint operator--(int) const { mint this_=*this; --*this; return this_; } mint operator-() const { return 0 - *this; } // static member functions static mint inv(mint x) { return inverse(x.value); } static mint m1pow(long long y) { return y%2?-1:1; } static mint pow(mint x, unsigned long long y) { mint ans=1; for(;y;y>>=1){ if(y&1ull) ans*=x; x*=x; } return ans; } // non-member functions mint& add_assign(mint y) { return *this+=y; } mint& sub_assign(mint y) { return *this-=y; } mint& mul_assign(mint y) { return *this*=y; } mint& div_assign(mint y) { return *this/=y; } mint& inv_assign() { return *this = inv(*this); } mint& pow_assign(unsigned long long y){ return *this = pow(*this, y); } mint add(mint y) const { mint ans=*this; return ans.add_assign(y); } mint sub(mint y) const { mint ans=*this; return ans.sub_assign(y); } mint mul(mint y) const { mint ans=*this; return ans.mul_assign(y); } mint div(mint y) const { mint ans=*this; return ans.div_assign(y); } mint inv() const { mint ans=*this; return ans.inv_assign(); } mint pow(unsigned long long y) const { return pow(*this, y); } mint square(mint x) const { return *this * *this; } mint cube(mint x) const { return *this * *this * *this; } template <class F> mint map(F const& f){ value=f(value); return *this; } }; template <class T> std::istream& operator>>(std::istream& is, modint<T>& x) { typename modint<T>::value_type y; is >> y; x = modint<T>{ y }; return is; } template <class T> std::ostream& operator<<(std::ostream& os, modint<T> x) { return os << x.value; } template <class T> modint<T> operator+(modint<T> x, modint<T> y) { return x+=y; } template <class T> modint<T> operator-(modint<T> x, modint<T> y) { return x-=y; } template <class T> modint<T> operator*(modint<T> x, modint<T> y) { return x*=y; } template <class T> modint<T> operator/(modint<T> x, modint<T> y) { return x/=y; } template <class T> bool operator==(modint<T> x, modint<T> y) { return x.value==y.value; } template <class T> bool operator!=(modint<T> x, modint<T> y) { return x.value!=y.value; } template <class T, class U> modint<T> operator+(modint<T> x, U y) { return x+modint<T>(y); } template <class T, class U> modint<T> operator-(modint<T> x, U y) { return x-modint<T>(y); } template <class T, class U> modint<T> operator*(modint<T> x, U y) { return x*modint<T>(y); } template <class T, class U> modint<T> operator/(modint<T> x, U y) { return x/modint<T>(y); } template <class T, class U> bool operator==(modint<T> x, U y) { return x==modint<T>(y); } template <class T, class U> bool operator!=(modint<T> x, U y) { return x!=modint<T>(y); } template <class T, class U> modint<T> operator+(U x, modint<T> y) { return modint<T>(x)+y; } template <class T, class U> modint<T> operator-(U x, modint<T> y) { return modint<T>(x)-y; } template <class T, class U> modint<T> operator*(U x, modint<T> y) { return modint<T>(x)*y; } template <class T, class U> modint<T> operator/(U x, modint<T> y) { return modint<T>(x)/y; } template <class T, class U> bool operator==(U x, modint<T> y) { return modint<T>(x)==y; } template <class T, class U> bool operator!=(U x, modint<T> y) { return modint<T>(x)!=y; } /*}}}*/ using mint = modint<std::integral_constant<i64, 1'000'000'007>>; template <class Mint> class residual_polynominals { using mint_type = Mint; public: vec<mint_type> f, qinv, qd; residual_polynominals()=default; residual_polynominals(residual_polynominals const&)=default; residual_polynominals(residual_polynominals&&)=default; residual_polynominals& operator=(residual_polynominals const&)=default; residual_polynominals& operator=(residual_polynominals&&)=default; ~residual_polynominals()=default; residual_polynominals(vec<mint> const& f_) : f(f_) { assert(usize{2} <= f.size()); qinv.resize(f.size()-1), qd.resize(f.size()-1); mint x = -f.front().inv(), y = -f.back().inv(); for (usize i=0; i<qinv.size(); i++) { qinv.at(i) = x * f.at(i+1); qd.at(i) = y * f.at(i); } } vec<mint>& normalize(vec<mint>& a) { while (a.size() < qd.size()) a.push_back(0); while (qd.size() < a.size()) { mint y = a.back(); a.pop_back(); for (usize i=0; i<qd.size(); i++) { a.at(a.size() - qd.size() + i) += y * qd.at(i); } } return a; } vec<mint> mul(vec<mint> a, vec<mint> b) { normalize(a), normalize(b); vec<mint> c(qd.size() * 2 - 1); for (usize i=0; i<qd.size(); i++) for (usize j=0; j<qd.size(); j++) { c.at(i+j) += a.at(i) * b.at(j); } return normalize(c); } vec<mint> pow(vec<mint> a, i64 b) { vec<mint> ans = {1}; for(; b; a = mul(a, a), b>>=1) if (b & i64{1}) ans = mul(ans, a); return ans; } }; int main() { std::cin.tie(nullptr); std::ios::sync_with_stdio(false); std::cout << std::setprecision(15) << std::fixed; usize d = 6; vec<mint> modulus(d+1, -mint::inv(d)); modulus.at(0) = 1; residual_polynominals<mint> rp(modulus); i64 n; std::cin >> n; std::cout << rp.pow(rp.qinv, n).front() << '\n'; }