Problem:
Problem E: LCM Count
Problem
1以上の整数 $N$ が与えられます。
1以上 $N$ 以下の整数からなる、重複のない有限個の要素を持つ整数列 $A_0,A_1,\ldots,A_{k-1}$ であって、 ${\rm lcm}(A_0,A_1,\ldots,A_{k-1})=N$
    となる数列の数を求めなさい。
    ここで、 ${\rm lcm}(A_0,A_1,\ldots,A_{k-1})$ は数列の全要素に対する最小公倍数を意味します。なお、答えは大きくなることがあるので、 $10^9+7$ で割った余りを求めてください。
Constraints
入力は以下の条件を満たす。
$1 \leq N \leq 10^{12}$
入力は整数である。
Input
入力は以下の形式で与えられる。
$N$
Output
問題文の条件を満たす数列の数を $10^9+7$ で割った余りを求めなさい。
    末尾の改行を忘れないこと。
Sample Input 1
1
Sample Output 1
1
条件を満たす数列は $\{1\}$ のみです。要素数が0であるような数列は考慮しません。
Sample Input 2
6
Sample Output 2
57
条件を満たす数列は、
$\{6\},\{1,6\},\{2,3\},\{2,6\},\{3,6\},\{1,2,3\},$
$\{1,2,6\},\{1,3,6\},\{2,3,6\},\{1,2,3,6\}$
を並べ替えてできる数列のみです。
$\{3,4\}$ や $\{2\}$ を並べ替えてできる数列は、最小公倍数がそれぞれ $12$ と $2$ であるため、条件を満たしません。
Sample Input 3
1000000000
Sample Output 3
919844582
$10^9+7$ で割った余りを出力してください。

Submitted solutions:

code_snippet: // competitive-verifier: PROBLEM
#include <cstdint>
#include <iostream>
#include <type_traits>
#include <utility>
namespace internal {
// @param m `1 <= m`
// @return x mod m
constexpr std::int64_t safe_mod(std::int64_t x, std::int64_t 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;
    std::uint64_t im;
    // @param m `1 <= m`
    explicit barrett(unsigned int m) : _m(m), im((std::uint64_t)(-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 {
        std::uint64_t z = a;
        z *= b;
        std::uint64_t x = (std::uint64_t)(((__uint128_t)(z)*im) >> 64);
        std::uint64_t y = x * _m;
        return (unsigned int)(z - y + (z < y ? _m : 0));
    }
};
struct montgomery {
    std::uint64_t _m;
    std::uint64_t im;
    std::uint64_t r2;
    // @param m `1 <= m`
    explicit constexpr montgomery(std::uint64_t m) : _m(m), im(m), r2(-__uint128_t(m) % m) {
        for (int i = 0; i < 5; ++i) im = im * (2 - _m * im);
        im = -im;
    }
    // @return m
    constexpr std::uint64_t umod() const { return _m; }
    // @param a `0 <= a < m`
    // @param b `0 <= b < m`
    // @return `a * b % m`
    constexpr std::uint64_t mul(std::uint64_t a, std::uint64_t b) const { return mr(mr(a, b), r2); }
    constexpr std::uint64_t exp(std::uint64_t a, std::uint64_t b) const {
        std::uint64_t res = 1, p = mr(a, r2);
        while (b) {
            if (b & 1) res = mr(res, p);
            p = mr(p, p);
            b >>= 1;
        }
        return res;
    }
    constexpr bool same_pow(std::uint64_t x, int s, std::uint64_t n) const {
        x = mr(x, r2), n = mr(n, r2);
        for (int r = 0; r < s; r++) {
            if (x == n) return true;
            x = mr(x, x);
        }
        return false;
    }
  private:
    constexpr std::uint64_t mr(std::uint64_t x) const {
        return ((__uint128_t)(x * im) * _m + x) >> 64;
    }
    constexpr std::uint64_t mr(std::uint64_t a, std::uint64_t b) const {
        __uint128_t t = (__uint128_t)a * b;
        std::uint64_t inc = std::uint64_t(t) != 0;
        std::uint64_t x = t >> 64, y = ((__uint128_t)(a * b * im) * _m) >> 64;
        unsigned long long z = 0;
        bool f = __builtin_uaddll_overflow(x, y, &z);
        z += inc;
        return f ? z - _m : z;
    }
};
constexpr bool is_SPRP32(std::uint32_t n, std::uint32_t a) {
    std::uint32_t d = n - 1, s = 0;
    while ((d & 1) == 0) ++s, d >>= 1;
    std::uint64_t cur = 1, pw = d;
    while (pw) {
        if (pw & 1) cur = (cur * a) % n;
        a = (std::uint64_t)a * a % n;
        pw >>= 1;
    }
    if (cur == 1) return true;
    for (std::uint32_t r = 0; r < s; r++) {
        if (cur == n - 1) return true;
        cur = cur * cur % n;
    }
    return false;
}
// given 2 <= n,a < 2^64, a prime, check whether n is a-SPRP
constexpr bool is_SPRP64(const montgomery &m, std::uint64_t a) {
    auto n = m.umod();
    if (n == a) return true;
    if (n % a == 0) return false;
    std::uint64_t d = n - 1;
    int s = 0;
    while ((d & 1) == 0) ++s, d >>= 1;
    std::uint64_t cur = m.exp(a, d);
    if (cur == 1) return true;
    return m.same_pow(cur, s, n - 1);
}
constexpr bool is_prime_constexpr(std::uint64_t x) {
    if (x == 2 || x == 3 || x == 5 || x == 7) return true;
    if (x % 2 == 0 || x % 3 == 0 || x % 5 == 0 || x % 7 == 0) return false;
    if (x < 121) return (x > 1);
    montgomery m(x);
    constexpr std::uint64_t bases[] = {2, 325, 9375, 28178, 450775, 9780504, 1795265022};
    for (auto a : bases) {
        if (!is_SPRP64(m, a)) return false;
    }
    return true;
}
constexpr bool is_prime_constexpr(std::int64_t x) {
    if (x < 0) return false;
    return is_prime_constexpr(std::uint64_t(x));
}
constexpr bool is_prime_constexpr(std::uint32_t x) {
    if (x == 2 || x == 3 || x == 5 || x == 7) return true;
    if (x % 2 == 0 || x % 3 == 0 || x % 5 == 0 || x % 7 == 0) return false;
    if (x < 121) return (x > 1);
    std::uint64_t h = x;
    h = ((h >> 16) ^ h) * 0x45d9f3b;
    h = ((h >> 16) ^ h) * 0x45d9f3b;
    h = ((h >> 16) ^ h) & 255;
    constexpr uint16_t bases[] = {
        15591, 2018,  166,   7429,  8064,  16045, 10503, 4399,  1949,  1295,  2776,  3620,  560,
        3128,  5212,  2657,  2300,  2021,  4652,  1471,  9336,  4018,  2398,  20462, 10277, 8028,
        2213,  6219,  620,   3763,  4852,  5012,  3185,  1333,  6227,  5298,  1074,  2391,  5113,
        7061,  803,   1269,  3875,  422,   751,   580,   4729,  10239, 746,   2951,  556,   2206,
        3778,  481,   1522,  3476,  481,   2487,  3266,  5633,  488,   3373,  6441,  3344,  17,
        15105, 1490,  4154,  2036,  1882,  1813,  467,   3307,  14042, 6371,  658,   1005,  903,
        737,   1887,  7447,  1888,  2848,  1784,  7559,  3400,  951,   13969, 4304,  177,   41,
        19875, 3110,  13221, 8726,  571,   7043,  6943,  1199,  352,   6435,  165,   1169,  3315,
        978,   233,   3003,  2562,  2994,  10587, 10030, 2377,  1902,  5354,  4447,  1555,  263,
        27027, 2283,  305,   669,   1912,  601,   6186,  429,   1930,  14873, 1784,  1661,  524,
        3577,  236,   2360,  6146,  2850,  55637, 1753,  4178,  8466,  222,   2579,  2743,  2031,
        2226,  2276,  374,   2132,  813,   23788, 1610,  4422,  5159,  1725,  3597,  3366,  14336,
        579,   165,   1375,  10018, 12616, 9816,  1371,  536,   1867,  10864, 857,   2206,  5788,
        434,   8085,  17618, 727,   3639,  1595,  4944,  2129,  2029,  8195,  8344,  6232,  9183,
        8126,  1870,  3296,  7455,  8947,  25017, 541,   19115, 368,   566,   5674,  411,   522,
        1027,  8215,  2050,  6544,  10049, 614,   774,   2333,  3007,  35201, 4706,  1152,  1785,
        1028,  1540,  3743,  493,   4474,  2521,  26845, 8354,  864,   18915, 5465,  2447,  42,
        4511,  1660,  166,   1249,  6259,  2553,  304,   272,   7286,  73,    6554,  899,   2816,
        5197,  13330, 7054,  2818,  3199,  811,   922,   350,   7514,  4452,  3449,  2663,  4708,
        418,   1621,  1171,  3471,  88,    11345, 412,   1559,  194};
    return is_SPRP32(x, bases[h]);
}
// @param n `0 <= n`
// @param m `1 <= m`
// @return `(x ** n) % m`
constexpr std::int64_t pow_mod_constexpr(std::int64_t x, std::int64_t n, int m) {
    if (m == 1) return 0;
    unsigned int _m = (unsigned int)(m);
    std::uint64_t r = 1;
    std::uint64_t 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;
    std::int64_t d = n - 1;
    while (d % 2 == 0) d /= 2;
    constexpr std::int64_t bases[3] = {2, 7, 61};
    for (std::int64_t a : bases) {
        std::int64_t t = d;
        std::int64_t 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<std::int64_t, std::int64_t> inv_gcd(std::int64_t a, std::int64_t b) {
    a = safe_mod(a, b);
    if (a == 0) return {b, 0};
    std::int64_t s = b, t = a;
    std::int64_t m0 = 0, m1 = 1;
    while (t) {
        std::int64_t u = s / t;
        s -= t * u;
        m0 -= m1 * u;
        auto tmp = s;
        s = t;
        t = tmp;
        tmp = m0;
        m0 = m1;
        m1 = tmp;
    }
    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; (std::int64_t)(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);
}  // namespace internal
#include <cassert>
#include <numeric>
namespace internal {
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;
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 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 constexpr mint raw(int v) {
        mint x;
        x._v = v;
        return x;
    }
    constexpr static_modint() : _v(0) {}
    template <class T, internal::is_signed_int_t<T> * = nullptr>
    constexpr static_modint(T v) : _v(0) {
        std::int64_t x = (std::int64_t)(v % (std::int64_t)(umod()));
        if (x < 0) x += umod();
        _v = (unsigned int)(x);
    }
    template <class T, internal::is_unsigned_int_t<T> * = nullptr>
    constexpr static_modint(T v) : _v(0) {
        _v = (unsigned int)(v % umod());
    }
    constexpr unsigned int val() const { return _v; }
    constexpr mint &operator++() {
        _v++;
        if (_v == umod()) _v = 0;
        return *this;
    }
    constexpr mint &operator--() {
        if (_v == 0) _v = umod();
        _v--;
        return *this;
    }
    constexpr mint operator++(int) {
        mint result = *this;
        ++*this;
        return result;
    }
    constexpr mint operator--(int) {
        mint result = *this;
        --*this;
        return result;
    }
    constexpr mint &operator+=(const mint &rhs) {
        _v += rhs._v;
        if (_v >= umod()) _v -= umod();
        return *this;
    }
    constexpr mint &operator-=(const mint &rhs) {
        _v -= rhs._v;
        if (_v >= umod()) _v += umod();
        return *this;
    }
    constexpr mint &operator*=(const mint &rhs) {
        std::uint64_t z = _v;
        z *= rhs._v;
        _v = (unsigned int)(z % umod());
        return *this;
    }
    constexpr mint &operator/=(const mint &rhs) { return *this = *this * rhs.inv(); }
    constexpr mint operator+() const { return *this; }
    constexpr mint operator-() const { return mint() - *this; }
    constexpr mint pow(std::int64_t n) const {
        assert(0 <= n);
        mint x = *this, r = 1;
        while (n) {
            if (n & 1) r *= x;
            x *= x;
            n >>= 1;
        }
        return r;
    }
    constexpr 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 constexpr mint operator+(const mint &lhs, const mint &rhs) { return mint(lhs) += rhs; }
    friend constexpr mint operator-(const mint &lhs, const mint &rhs) { return mint(lhs) -= rhs; }
    friend constexpr mint operator*(const mint &lhs, const mint &rhs) { return mint(lhs) *= rhs; }
    friend constexpr mint operator/(const mint &lhs, const mint &rhs) { return mint(lhs) /= rhs; }
    friend constexpr bool operator==(const mint &lhs, const mint &rhs) { return lhs._v == rhs._v; }
    friend constexpr bool operator!=(const mint &lhs, const mint &rhs) { return lhs._v != rhs._v; }
    friend std::istream &operator>>(std::istream &is, mint &rhs) {
        std::int64_t t;
        is >> t;
        rhs = mint(t);
        return is;
    }
    friend constexpr std::ostream &operator<<(std::ostream &os, const mint &rhs) {
        return os << 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) {
        std::int64_t x = (std::int64_t)(v % (std::int64_t)(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(std::int64_t 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; }
    friend std::istream &operator>>(std::istream &is, mint &rhs) {
        std::int64_t t;
        is >> t;
        rhs = mint(t);
        return is;
    }
    friend constexpr std::ostream &operator<<(std::ostream &os, const mint &rhs) {
        return os << 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 modint998 = static_modint<998244353>;
using modint107 = 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
#include <algorithm>
#include <bitset>
#include <iterator>
#include <vector>
/**
 * @brief 素数ライブラリ
 *
 * @tparam N
 */
template <int N = 1 << 22>
struct prime_number {
    prime_number() : is_not_prime(), data() { init(); }
    /**
     * @brief 素数判定
     *
     * @param n
     * @return bool
     */
    bool is_prime(std::int64_t n) const {
        assert(n >= 0);
        if (n < N) return !is_not_prime[n];
        for (auto i : data) {
            if ((std::int64_t)i * i > n) break;
            if (n % i == 0) return false;
        }
        return true;
    }
    std::vector<int> prime_numbers(int x) const {
        std::vector<int> res;
        for (auto i : data) {
            if (i > x) break;
            res.emplace_back(i);
        }
        return res;
    }
    /**
     * @brief 素因数分解
     *
     * @tparam T
     * @param x
     * @return std::vector<std::pair<T, int>>
     */
    template <class T>
    std::vector<std::pair<T, int>> prime_factorization(T x) const {
        if (x == 1) return std::vector<std::pair<T, int>>();
        std::vector<std::pair<T, int>> res;
        for (auto p : data) {
            int cnt = 0;
            for (; x % p == 0; x /= p) ++cnt;
            if (cnt) res.emplace_back(p, cnt);
            if ((std::int64_t)p * p > x) break;
        }
        if (x != 1) res.emplace_back(x, 1);
        return res;
    }
    /**
     * @brief 約数列挙
     *
     * @tparam T
     * @param x
     * @return std::vector<T>
     */
    template <class T>
    std::vector<T> divisors(T x) const {
        if (x == 1) return std::vector<T>(1, 1);
        auto v = prime_factorization(x);
        std::vector<T> res;
        res.emplace_back(1);
        for (auto p : v) {
            int n = res.size();
            res.resize(n * (p.second + 1));
            for (int i = 0; i < n * p.second; ++i) res[n + i] = res[i] * p.first;
            for (int i = 1; i <= p.second; ++i) {
                std::inplace_merge(res.begin(), res.begin() + n * i, res.begin() + n * (i + 1));
            }
        }
        return res;
    }
    /**
     * @brief 因数分解列挙
     *
     * @tparam T
     * @param x
     * @return std::vector<std::vector<T>>
     */
    template <class T>
    std::vector<std::vector<T>> factorization(T x) const {
        std::vector<std::vector<T>> res;
        auto f = [&](auto self, std::vector<T> v, T a) -> void {
            if (a == 1) res.emplace_back(v);
            for (auto i : this->divisors(a)) {
                if (i == 1 || (!v.empty() && v.back() > i)) continue;
                v.emplace_back(i);
                self(self, v, a / i);
                v.pop_back();
            }
        };
        f(f, std::vector<T>(), x);
        return res;
    }
  private:
    std::bitset<N> is_not_prime;
    std::vector<int> data;
    void init() {
        is_not_prime[0] = is_not_prime[1] = true;
        for (int i = 2; i < N; ++i) {
            if (!is_not_prime[i]) {
                data.emplace_back(i);
                if ((std::int64_t)i * i >= N) continue;
                if (i == 2) {
                    for (int j = i * i; j < N; j += i) is_not_prime[j] = true;
                } else {
                    for (int j = i * i; j < N; j += i << 1) is_not_prime[j] = true;
                }
            }
        }
    }
};
#ifdef ATCODER
#pragma GCC target("sse4.2,avx512f,avx512dq,avx512ifma,avx512cd,avx512bw,avx512vl,bmi2")
#endif
#pragma GCC optimize("Ofast,fast-math,unroll-all-loops")
#include <bits/stdc++.h>
#ifndef ATCODER
#pragma GCC target("sse4.2,avx2,bmi2")
#endif
template <class T, class U>
constexpr bool chmax(T &a, const U &b) {
    return a < (T)b ? a = (T)b, true : false;
}
template <class T, class U>
constexpr bool chmin(T &a, const U &b) {
    return (T)b < a ? a = (T)b, true : false;
}
constexpr std::int64_t INF = 1000000000000000003;
constexpr int Inf = 1000000003;
constexpr double EPS = 1e-7;
constexpr double PI = 3.14159265358979323846;
#define FOR(i, m, n) for (int i = (m); i < int(n); ++i)
#define FORR(i, m, n) for (int i = (m)-1; i >= int(n); --i)
#define FORL(i, m, n) for (int64_t i = (m); i < int64_t(n); ++i)
#define rep(i, n) FOR (i, 0, n)
#define repn(i, n) FOR (i, 1, n + 1)
#define repr(i, n) FORR (i, n, 0)
#define repnr(i, n) FORR (i, n + 1, 1)
#define all(s) (s).begin(), (s).end()
struct Sonic {
    Sonic() {
        std::ios::sync_with_stdio(false);
        std::cin.tie(nullptr);
        std::cout << std::fixed << std::setprecision(20);
    }
    constexpr void operator()() const {}
} sonic;
using namespace std;
using ll = std::int64_t;
using ld = long double;
template <class T, class U>
std::istream &operator>>(std::istream &is, std::pair<T, U> &p) {
    return is >> p.first >> p.second;
}
template <class T>
std::istream &operator>>(std::istream &is, std::vector<T> &v) {
    for (T &i : v) is >> i;
    return is;
}
template <class T, class U>
std::ostream &operator<<(std::ostream &os, const std::pair<T, U> &p) {
    return os << '(' << p.first << ',' << p.second << ')';
}
template <class T>
std::ostream &operator<<(std::ostream &os, const std::vector<T> &v) {
    for (auto it = v.begin(); it != v.end(); ++it) os << (it == v.begin() ? "" : " ") << *it;
    return os;
}
template <class Head, class... Tail>
void co(Head &&head, Tail &&...tail) {
    if constexpr (sizeof...(tail) == 0) std::cout << head << '\n';
    else std::cout << head << ' ', co(std::forward<Tail>(tail)...);
}
template <class Head, class... Tail>
void ce(Head &&head, Tail &&...tail) {
    if constexpr (sizeof...(tail) == 0) std::cerr << head << '\n';
    else std::cerr << head << ' ', ce(std::forward<Tail>(tail)...);
}
void Yes(bool is_correct = true) { std::cout << (is_correct ? "Yes\n" : "No\n"); }
void No(bool is_not_correct = true) { Yes(!is_not_correct); }
void YES(bool is_correct = true) { std::cout << (is_correct ? "YES\n" : "NO\n"); }
void NO(bool is_not_correct = true) { YES(!is_not_correct); }
void Takahashi(bool is_correct = true) { std::cout << (is_correct ? "Takahashi" : "Aoki") << '\n'; }
void Aoki(bool is_not_correct = true) { Takahashi(!is_not_correct); }
using Mint = modint107;
prime_number pn;
int main(void) {
    ll n;
    cin >> n;
    if (n == 1) {
        co(1);
        return 0;
    }
    auto v = pn.prime_factorization(n);
    int m = v.size();
    Mint ans = 0;
    rep (bit, 1 << m) {
        ll sum = 1;
        int c = 0;
        rep (i, m) {
            if (~bit >> i & 1) {
                sum *= v[i].second + 1;
            } else {
                ++c;
                sum *= v[i].second;
            }
        }
        Mint p = 1;
        Mint x = 0;
        repnr (i, sum) {
            p *= i;
            x += p;
        }
        if (c & 1) {
            ans -= x;
        } else {
            ans += x;
        }
    }
    co(ans);
    return 0;
}
accuracy: 1
time_ms: 10
memory_kb: 6492
final_rank: 1

code_snippet: // competitive-verifier: PROBLEM
#include <cstdint>
#include <iostream>
#include <type_traits>
#include <utility>
namespace internal {
// @param m `1 <= m`
// @return x mod m
constexpr std::int64_t safe_mod(std::int64_t x, std::int64_t 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;
    std::uint64_t im;
    // @param m `1 <= m`
    explicit barrett(unsigned int m) : _m(m), im((std::uint64_t)(-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 {
        std::uint64_t z = a;
        z *= b;
        std::uint64_t x = (std::uint64_t)(((__uint128_t)(z)*im) >> 64);
        std::uint64_t y = x * _m;
        return (unsigned int)(z - y + (z < y ? _m : 0));
    }
};
struct montgomery {
    std::uint64_t _m;
    std::uint64_t im;
    std::uint64_t r2;
    // @param m `1 <= m`
    explicit constexpr montgomery(std::uint64_t m) : _m(m), im(m), r2(-__uint128_t(m) % m) {
        for (int i = 0; i < 5; ++i) im = im * (2 - _m * im);
        im = -im;
    }
    // @return m
    constexpr std::uint64_t umod() const { return _m; }
    // @param a `0 <= a < m`
    // @param b `0 <= b < m`
    // @return `a * b % m`
    constexpr std::uint64_t mul(std::uint64_t a, std::uint64_t b) const { return mr(mr(a, b), r2); }
    constexpr std::uint64_t exp(std::uint64_t a, std::uint64_t b) const {
        std::uint64_t res = 1, p = mr(a, r2);
        while (b) {
            if (b & 1) res = mr(res, p);
            p = mr(p, p);
            b >>= 1;
        }
        return res;
    }
    constexpr bool same_pow(std::uint64_t x, int s, std::uint64_t n) const {
        x = mr(x, r2), n = mr(n, r2);
        for (int r = 0; r < s; r++) {
            if (x == n) return true;
            x = mr(x, x);
        }
        return false;
    }
  private:
    constexpr std::uint64_t mr(std::uint64_t x) const {
        return ((__uint128_t)(x * im) * _m + x) >> 64;
    }
    constexpr std::uint64_t mr(std::uint64_t a, std::uint64_t b) const {
        __uint128_t t = (__uint128_t)a * b;
        std::uint64_t inc = std::uint64_t(t) != 0;
        std::uint64_t x = t >> 64, y = ((__uint128_t)(a * b * im) * _m) >> 64;
        unsigned long long z = 0;
        bool f = __builtin_uaddll_overflow(x, y, &z);
        z += inc;
        return f ? z - _m : z;
    }
};
constexpr bool is_SPRP32(std::uint32_t n, std::uint32_t a) {
    std::uint32_t d = n - 1, s = 0;
    while ((d & 1) == 0) ++s, d >>= 1;
    std::uint64_t cur = 1, pw = d;
    while (pw) {
        if (pw & 1) cur = (cur * a) % n;
        a = (std::uint64_t)a * a % n;
        pw >>= 1;
    }
    if (cur == 1) return true;
    for (std::uint32_t r = 0; r < s; r++) {
        if (cur == n - 1) return true;
        cur = cur * cur % n;
    }
    return false;
}
// given 2 <= n,a < 2^64, a prime, check whether n is a-SPRP
constexpr bool is_SPRP64(const montgomery &m, std::uint64_t a) {
    auto n = m.umod();
    if (n == a) return true;
    if (n % a == 0) return false;
    std::uint64_t d = n - 1;
    int s = 0;
    while ((d & 1) == 0) ++s, d >>= 1;
    std::uint64_t cur = m.exp(a, d);
    if (cur == 1) return true;
    return m.same_pow(cur, s, n - 1);
}
constexpr bool is_prime_constexpr(std::uint64_t x) {
    if (x == 2 || x == 3 || x == 5 || x == 7) return true;
    if (x % 2 == 0 || x % 3 == 0 || x % 5 == 0 || x % 7 == 0) return false;
    if (x < 121) return (x > 1);
    montgomery m(x);
    constexpr std::uint64_t bases[] = {2, 325, 9375, 28178, 450775, 9780504, 1795265022};
    for (auto a : bases) {
        if (!is_SPRP64(m, a)) return false;
    }
    return true;
}
constexpr bool is_prime_constexpr(std::int64_t x) {
    if (x < 0) return false;
    return is_prime_constexpr(std::uint64_t(x));
}
constexpr bool is_prime_constexpr(std::uint32_t x) {
    if (x == 2 || x == 3 || x == 5 || x == 7) return true;
    if (x % 2 == 0 || x % 3 == 0 || x % 5 == 0 || x % 7 == 0) return false;
    if (x < 121) return (x > 1);
    std::uint64_t h = x;
    h = ((h >> 16) ^ h) * 0x45d9f3b;
    h = ((h >> 16) ^ h) * 0x45d9f3b;
    h = ((h >> 16) ^ h) & 255;
    constexpr uint16_t bases[] = {
        15591, 2018,  166,   7429,  8064,  16045, 10503, 4399,  1949,  1295,  2776,  3620,  560,
        3128,  5212,  2657,  2300,  2021,  4652,  1471,  9336,  4018,  2398,  20462, 10277, 8028,
        2213,  6219,  620,   3763,  4852,  5012,  3185,  1333,  6227,  5298,  1074,  2391,  5113,
        7061,  803,   1269,  3875,  422,   751,   580,   4729,  10239, 746,   2951,  556,   2206,
        3778,  481,   1522,  3476,  481,   2487,  3266,  5633,  488,   3373,  6441,  3344,  17,
        15105, 1490,  4154,  2036,  1882,  1813,  467,   3307,  14042, 6371,  658,   1005,  903,
        737,   1887,  7447,  1888,  2848,  1784,  7559,  3400,  951,   13969, 4304,  177,   41,
        19875, 3110,  13221, 8726,  571,   7043,  6943,  1199,  352,   6435,  165,   1169,  3315,
        978,   233,   3003,  2562,  2994,  10587, 10030, 2377,  1902,  5354,  4447,  1555,  263,
        27027, 2283,  305,   669,   1912,  601,   6186,  429,   1930,  14873, 1784,  1661,  524,
        3577,  236,   2360,  6146,  2850,  55637, 1753,  4178,  8466,  222,   2579,  2743,  2031,
        2226,  2276,  374,   2132,  813,   23788, 1610,  4422,  5159,  1725,  3597,  3366,  14336,
        579,   165,   1375,  10018, 12616, 9816,  1371,  536,   1867,  10864, 857,   2206,  5788,
        434,   8085,  17618, 727,   3639,  1595,  4944,  2129,  2029,  8195,  8344,  6232,  9183,
        8126,  1870,  3296,  7455,  8947,  25017, 541,   19115, 368,   566,   5674,  411,   522,
        1027,  8215,  2050,  6544,  10049, 614,   774,   2333,  3007,  35201, 4706,  1152,  1785,
        1028,  1540,  3743,  493,   4474,  2521,  26845, 8354,  864,   18915, 5465,  2447,  42,
        4511,  1660,  166,   1249,  6259,  2553,  304,   272,   7286,  73,    6554,  899,   2816,
        5197,  13330, 7054,  2818,  3199,  811,   922,   350,   7514,  4452,  3449,  2663,  4708,
        418,   1621,  1171,  3471,  88,    11345, 412,   1559,  194};
    return is_SPRP32(x, bases[h]);
}
// @param n `0 <= n`
// @param m `1 <= m`
// @return `(x ** n) % m`
constexpr std::int64_t pow_mod_constexpr(std::int64_t x, std::int64_t n, int m) {
    if (m == 1) return 0;
    unsigned int _m = (unsigned int)(m);
    std::uint64_t r = 1;
    std::uint64_t 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;
    std::int64_t d = n - 1;
    while (d % 2 == 0) d /= 2;
    constexpr std::int64_t bases[3] = {2, 7, 61};
    for (std::int64_t a : bases) {
        std::int64_t t = d;
        std::int64_t 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<std::int64_t, std::int64_t> inv_gcd(std::int64_t a, std::int64_t b) {
    a = safe_mod(a, b);
    if (a == 0) return {b, 0};
    std::int64_t s = b, t = a;
    std::int64_t m0 = 0, m1 = 1;
    while (t) {
        std::int64_t u = s / t;
        s -= t * u;
        m0 -= m1 * u;
        auto tmp = s;
        s = t;
        t = tmp;
        tmp = m0;
        m0 = m1;
        m1 = tmp;
    }
    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; (std::int64_t)(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);
}  // namespace internal
#include <cassert>
#include <numeric>
namespace internal {
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;
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 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 constexpr mint raw(int v) {
        mint x;
        x._v = v;
        return x;
    }
    constexpr static_modint() : _v(0) {}
    template <class T, internal::is_signed_int_t<T> * = nullptr>
    constexpr static_modint(T v) : _v(0) {
        std::int64_t x = (std::int64_t)(v % (std::int64_t)(umod()));
        if (x < 0) x += umod();
        _v = (unsigned int)(x);
    }
    template <class T, internal::is_unsigned_int_t<T> * = nullptr>
    constexpr static_modint(T v) : _v(0) {
        _v = (unsigned int)(v % umod());
    }
    constexpr unsigned int val() const { return _v; }
    constexpr mint &operator++() {
        _v++;
        if (_v == umod()) _v = 0;
        return *this;
    }
    constexpr mint &operator--() {
        if (_v == 0) _v = umod();
        _v--;
        return *this;
    }
    constexpr mint operator++(int) {
        mint result = *this;
        ++*this;
        return result;
    }
    constexpr mint operator--(int) {
        mint result = *this;
        --*this;
        return result;
    }
    constexpr mint &operator+=(const mint &rhs) {
        _v += rhs._v;
        if (_v >= umod()) _v -= umod();
        return *this;
    }
    constexpr mint &operator-=(const mint &rhs) {
        _v -= rhs._v;
        if (_v >= umod()) _v += umod();
        return *this;
    }
    constexpr mint &operator*=(const mint &rhs) {
        std::uint64_t z = _v;
        z *= rhs._v;
        _v = (unsigned int)(z % umod());
        return *this;
    }
    constexpr mint &operator/=(const mint &rhs) { return *this = *this * rhs.inv(); }
    constexpr mint operator+() const { return *this; }
    constexpr mint operator-() const { return mint() - *this; }
    constexpr mint pow(std::int64_t n) const {
        assert(0 <= n);
        mint x = *this, r = 1;
        while (n) {
            if (n & 1) r *= x;
            x *= x;
            n >>= 1;
        }
        return r;
    }
    constexpr 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 constexpr mint operator+(const mint &lhs, const mint &rhs) { return mint(lhs) += rhs; }
    friend constexpr mint operator-(const mint &lhs, const mint &rhs) { return mint(lhs) -= rhs; }
    friend constexpr mint operator*(const mint &lhs, const mint &rhs) { return mint(lhs) *= rhs; }
    friend constexpr mint operator/(const mint &lhs, const mint &rhs) { return mint(lhs) /= rhs; }
    friend constexpr bool operator==(const mint &lhs, const mint &rhs) { return lhs._v == rhs._v; }
    friend constexpr bool operator!=(const mint &lhs, const mint &rhs) { return lhs._v != rhs._v; }
    friend std::istream &operator>>(std::istream &is, mint &rhs) {
        std::int64_t t;
        is >> t;
        rhs = mint(t);
        return is;
    }
    friend constexpr std::ostream &operator<<(std::ostream &os, const mint &rhs) {
        return os << 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) {
        std::int64_t x = (std::int64_t)(v % (std::int64_t)(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(std::int64_t 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; }
    friend std::istream &operator>>(std::istream &is, mint &rhs) {
        std::int64_t t;
        is >> t;
        rhs = mint(t);
        return is;
    }
    friend constexpr std::ostream &operator<<(std::ostream &os, const mint &rhs) {
        return os << 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 modint998 = static_modint<998244353>;
using modint107 = 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
#include <algorithm>
#include <bitset>
#include <iterator>
#include <vector>
/**
 * @brief 素数ライブラリ
 *
 * @tparam N
 */
template <int N = 1 << 22>
struct prime_number {
    prime_number() : is_not_prime(), data() { init(); }
    /**
     * @brief 素数判定
     *
     * @param n
     * @return bool
     */
    bool is_prime(std::int64_t n) const {
        assert(n >= 0);
        if (n < N) return !is_not_prime[n];
        for (auto i : data) {
            if ((std::int64_t)i * i > n) break;
            if (n % i == 0) return false;
        }
        return true;
    }
    std::vector<int> prime_numbers(int x) const {
        std::vector<int> res;
        for (auto i : data) {
            if (i > x) break;
            res.emplace_back(i);
        }
        return res;
    }
    /**
     * @brief 素因数分解
     *
     * @tparam T
     * @param x
     * @return std::vector<std::pair<T, int>>
     */
    template <class T>
    std::vector<std::pair<T, int>> prime_factorization(T x) const {
        if (x == 1) return std::vector<std::pair<T, int>>();
        std::vector<std::pair<T, int>> res;
        for (auto p : data) {
            int cnt = 0;
            for (; x % p == 0; x /= p) ++cnt;
            if (cnt) res.emplace_back(p, cnt);
            if ((std::int64_t)p * p > x) break;
        }
        if (x != 1) res.emplace_back(x, 1);
        return res;
    }
    /**
     * @brief 約数列挙
     *
     * @tparam T
     * @param x
     * @return std::vector<T>
     */
    template <class T>
    std::vector<T> divisors(T x) const {
        if (x == 1) return std::vector<T>(1, 1);
        auto v = prime_factorization(x);
        std::vector<T> res;
        res.emplace_back(1);
        for (auto p : v) {
            int n = res.size();
            res.resize(n * (p.second + 1));
            for (int i = 0; i < n * p.second; ++i) res[n + i] = res[i] * p.first;
            for (int i = 1; i <= p.second; ++i) {
                std::inplace_merge(res.begin(), res.begin() + n * i, res.begin() + n * (i + 1));
            }
        }
        return res;
    }
    /**
     * @brief 因数分解列挙
     *
     * @tparam T
     * @param x
     * @return std::vector<std::vector<T>>
     */
    template <class T>
    std::vector<std::vector<T>> factorization(T x) const {
        std::vector<std::vector<T>> res;
        auto f = [&](auto self, std::vector<T> v, T a) -> void {
            if (a == 1) res.emplace_back(v);
            for (auto i : this->divisors(a)) {
                if (i == 1 || (!v.empty() && v.back() > i)) continue;
                v.emplace_back(i);
                self(self, v, a / i);
                v.pop_back();
            }
        };
        f(f, std::vector<T>(), x);
        return res;
    }
  private:
    std::bitset<N> is_not_prime;
    std::vector<int> data;
    void init() {
        is_not_prime[0] = is_not_prime[1] = true;
        for (int i = 2; i < N; ++i) {
            if (!is_not_prime[i]) {
                data.emplace_back(i);
                if ((std::int64_t)i * i >= N) continue;
                if (i == 2) {
                    for (int j = i * i; j < N; j += i) is_not_prime[j] = true;
                } else {
                    for (int j = i * i; j < N; j += i << 1) is_not_prime[j] = true;
                }
            }
        }
    }
};
#ifdef ATCODER
#pragma GCC target("sse4.2,avx512f,avx512dq,avx512ifma,avx512cd,avx512bw,avx512vl,bmi2")
#endif
#pragma GCC optimize("Ofast,fast-math,unroll-all-loops")
#include <bits/stdc++.h>
#ifndef ATCODER
#pragma GCC target("sse4.2,avx2,bmi2")
#endif
template <class T, class U>
constexpr bool chmax(T &a, const U &b) {
    return a < (T)b ? a = (T)b, true : false;
}
template <class T, class U>
constexpr bool chmin(T &a, const U &b) {
    return (T)b < a ? a = (T)b, true : false;
}
constexpr std::int64_t INF = 1000000000000000003;
constexpr int Inf = 1000000003;
constexpr double EPS = 1e-7;
constexpr double PI = 3.14159265358979323846;
#define FOR(i, m, n) for (int i = (m); i < int(n); ++i)
#define FORR(i, m, n) for (int i = (m)-1; i >= int(n); --i)
#define FORL(i, m, n) for (int64_t i = (m); i < int64_t(n); ++i)
#define rep(i, n) FOR (i, 0, n)
#define repn(i, n) FOR (i, 1, n + 1)
#define repr(i, n) FORR (i, n, 0)
#define repnr(i, n) FORR (i, n + 1, 1)
#define all(s) (s).begin(), (s).end()
struct Sonic {
    Sonic() {
        std::ios::sync_with_stdio(false);
        std::cin.tie(nullptr);
        std::cout << std::fixed << std::setprecision(20);
    }
    constexpr void operator()() const {}
} sonic;
using namespace std;
using ll = std::int64_t;
using ld = long double;
template <class T, class U>
std::istream &operator>>(std::istream &is, std::pair<T, U> &p) {
    return is >> p.first >> p.second;
}
template <class T>
std::istream &operator>>(std::istream &is, std::vector<T> &v) {
    for (T &i : v) is >> i;
    return is;
}
template <class T, class U>
std::ostream &operator<<(std::ostream &os, const std::pair<T, U> &p) {
    return os << '(' << p.first << ',' << p.second << ')';
}
template <class T>
std::ostream &operator<<(std::ostream &os, const std::vector<T> &v) {
    for (auto it = v.begin(); it != v.end(); ++it) os << (it == v.begin() ? "" : " ") << *it;
    return os;
}
template <class Head, class... Tail>
void co(Head &&head, Tail &&...tail) {
    if constexpr (sizeof...(tail) == 0) std::cout << head << '\n';
    else std::cout << head << ' ', co(std::forward<Tail>(tail)...);
}
template <class Head, class... Tail>
void ce(Head &&head, Tail &&...tail) {
    if constexpr (sizeof...(tail) == 0) std::cerr << head << '\n';
    else std::cerr << head << ' ', ce(std::forward<Tail>(tail)...);
}
void Yes(bool is_correct = true) { std::cout << (is_correct ? "Yes\n" : "No\n"); }
void No(bool is_not_correct = true) { Yes(!is_not_correct); }
void YES(bool is_correct = true) { std::cout << (is_correct ? "YES\n" : "NO\n"); }
void NO(bool is_not_correct = true) { YES(!is_not_correct); }
void Takahashi(bool is_correct = true) { std::cout << (is_correct ? "Takahashi" : "Aoki") << '\n'; }
void Aoki(bool is_not_correct = true) { Takahashi(!is_not_correct); }
using Mint = modint107;
prime_number pn;
int main(void) {
    ll n;
    cin >> n;
    if (n == 1) {
        co(1);
        return 0;
    }
    auto v = pn.prime_factorization(n);
    int m = v.size();
    Mint ans = 0;
    rep (bit, 1 << m) {
        ll sum = 1;
        int c = 0;
        rep (i, m) {
            if (~bit >> i & 1) {
                ++c;
                sum *= v[i].second + 1;
            } else {
                sum *= v[i].second;
            }
        }
        Mint p = 1;
        Mint x = 0;
        repnr (i, sum) {
            p *= i;
            x += p;
        }
        if (c & 1) {
            ans -= x;
        } else {
            ans += x;
        }
    }
    co(ans);
    return 0;
}
accuracy: 0.12121212121212122
time_ms: 10
memory_kb: 5524
final_rank: 18

code_snippet: #include <bits/stdc++.h>
//#include <atcoder/all>
//using namespace atcoder;
#pragma GCC target ("avx2")
#pragma GCC optimization ("O3")
#pragma GCC optimization ("unroll-loops")
using namespace std;
 
typedef vector<int> VI;
typedef vector<VI> VVI;
typedef vector<string> VS;
typedef pair<int, int> PII;
typedef pair<int, int> pii;
typedef pair<long long, long long> PLL;
typedef pair<int, PII> TIII;
 
typedef long long ll;
typedef long double ld;
typedef unsigned long long ull;
 
 
#define FOR(i, s, n) for (int i = s; i < (int)n; ++i)
#define REP(i, n) FOR(i, 0, n)
#define rep(i, a, b) for (int i = a; i < (b); ++i)
#define trav(a, x) for (auto &a : x)
#define all(x) x.begin(), x.end()
 
#define MOD 1000000007
 
template<class T1, class T2> inline bool chmax(T1 &a, T2 b) {if (a < b) {a = b; return true;} return false;}
template<class T1, class T2> inline bool chmin(T1 &a, T2 b) {if (a > b) {a = b; return true;} return false;}
const double EPS = 1e-8, PI = acos(-1);
const double pi = 3.141592653589793238462643383279;
//ここから編集    
typedef string::const_iterator State;
ll GCD(ll a, ll b){
  return (b==0)?a:GCD(b, a%b);
}
ll LCM(ll a, ll b){
  return a/GCD(a, b) * b;
}
template< int mod >
struct ModInt {
  int x;
 
  ModInt() : x(0) {}
 
  ModInt(int64_t y) : x(y >= 0 ? y % mod : (mod - (-y) % mod) % mod) {}
 
  ModInt &operator+=(const ModInt &p) {
    if((x += p.x) >= mod) x -= mod;
    return *this;
  }
 
  ModInt &operator-=(const ModInt &p) {
    if((x += mod - p.x) >= mod) x -= mod;
    return *this;
  }
 
  ModInt &operator*=(const ModInt &p) {
    x = (int) (1LL * x * p.x % mod);
    return *this;
  }
 
  ModInt &operator/=(const ModInt &p) {
    *this *= p.inverse();
    return *this;
  }
 
  ModInt operator-() const { return ModInt(-x); }
 
  ModInt operator+(const ModInt &p) const { return ModInt(*this) += p; }
 
  ModInt operator-(const ModInt &p) const { return ModInt(*this) -= p; }
 
  ModInt operator*(const ModInt &p) const { return ModInt(*this) *= p; }
 
  ModInt operator/(const ModInt &p) const { return ModInt(*this) /= p; }
 
  bool operator==(const ModInt &p) const { return x == p.x; }
 
  bool operator!=(const ModInt &p) const { return x != p.x; }
 
  ModInt inverse() const {
    int a = x, b = mod, u = 1, v = 0, t;
    while(b > 0) {
      t = a / b;
      swap(a -= t * b, b);
      swap(u -= t * v, v);
    }
    return ModInt(u);
  }
 
  ModInt pow(int64_t n) const {
    ModInt ret(1), mul(x);
    while(n > 0) {
      if(n & 1) ret *= mul;
      mul *= mul;
      n >>= 1;
    }
    return ret;
  }
 
  friend ostream &operator<<(ostream &os, const ModInt &p) {
    return os << p.x;
  }
 
  friend istream &operator>>(istream &is, ModInt &a) {
    int64_t t;
    is >> t;
    a = ModInt< mod >(t);
    return (is);
  }
 
  static int get_mod() { return mod; }
};
 
using modint = ModInt< 1000000007 >;
template< typename T >
struct Combination {
  vector< T > _fact, _rfact, _inv;
 
  Combination(int sz) : _fact(sz + 1), _rfact(sz + 1), _inv(sz + 1) {
    _fact[0] = _rfact[sz] = _inv[0] = 1;
    for(int i = 1; i <= sz; i++) _fact[i] = _fact[i - 1] * i;
    _rfact[sz] /= _fact[sz];
    for(int i = sz - 1; i >= 0; i--) _rfact[i] = _rfact[i + 1] * (i + 1);
    for(int i = 1; i <= sz; i++) _inv[i] = _rfact[i] * _fact[i - 1];
  }
 
  inline T fact(int k) const { return _fact[k]; }
 
  inline T rfact(int k) const { return _rfact[k]; }
 
  inline T inv(int k) const { return _inv[k]; }
 
  T P(int n, int r) const {
    if(r < 0 || n < r) return 0;
    return fact(n) * rfact(n - r);
  }
 
  T C(int p, int q) const {
    if(q < 0 || p < q) return 0;
    return fact(p) * rfact(q) * rfact(p - q);
  }
 
  T H(int n, int r) const {
    if(n < 0 || r < 0) return (0);
    return r == 0 ? 1 : C(n + r - 1, r);
  }
};
 
ll modpow(ll x, ll n, ll mod) {
  ll res = 1;
  x %= mod;
  if(x == 0) return 0;
  while(n) {
    if(n&1) res = (res * x) % mod;
    x = (x * x) % mod;
    n >>= 1;
  }
  return res;
} 
inline long long mod(long long a, long long m) {
    return (a % m + m) % m;
}
template<typename T> 
struct BIT{
  int N;
  std::vector<T> node;
  BIT(){}
  BIT(int n){
    N = n;
    node.resize(N+10);
  }
  void build(int n) {
    N = n;
    node.resize(N+10);
  }
  /* a: 1-indexed */
  void add(int a, T x){
    for(int i=a; i<(int)node.size(); i += i & -i) node[i] += x;
  }

  /* [1, a] */
  T sum(int a){
    T res = 0;
    for(int x=a; x>0; x -= x & -x) res += node[x];
    return res;
  }

  /* [l, r] */
  T rangesum(int l, int r){
    return sum(r) - sum(l-1);
  }

  /* 
    a1+a2+...+aw >= valとなるような最小のwを返す
    @verify https://codeforces.com/contest/992/problem/E
  */
  int lower_bound(T val) {
    if(val < 0) return 0;

    int res = 0;
    int n = 1; 
    while (n < N) n *= 2;

    T tv=0;
    for (int k = n; k > 0; k /= 2) {
      if(res + k < N && node[res + k] < val){
        val -= node[res+k];
        res += k;
      }
    }
    return res+1; 
  }
};
struct UnionFind{
  std::vector<int> par;
  std::vector<int> siz;

  UnionFind(int sz_): par(sz_), siz(sz_) {
    for(int i=0; i<sz_; ++i) par[i] = i, siz[i] = 1;
  }

  void init(int sz_){
    par.resize(sz_);
    siz.resize(sz_);
    for(int i=0; i<sz_; ++i) par[i] = i, siz[i] = 1;
  }

  int root(int x){
    if(x == par[x]) return x;
    return par[x] = root(par[x]);
  }

  bool merge(int x, int y){
    x = root(x), y = root(y);
    if(x == y) return false;
    if(siz[x] < siz[y]) std::swap(x, y);
    siz[x] += siz[y];
    par[y] = x;
    return true;
  }

  bool issame(int x, int y){
    return root(x) == root(y);
  }

  int size(int x){
    return siz[root(x)];
  }
};
struct RollingHash{

    using ull = unsigned long long;
    const ull mod = (1ULL << 61) - 1;
    const ull MASK30 = (1ULL << 30) - 1;
    const ull MASK31 = (1ULL << 31) - 1;

    const ull MASK61 = mod;

    ull base;
    int n;
    vector<ull> hash, pow;

    RollingHash(const string &s)
    {
        random_device rnd;
        mt19937_64 mt(rnd());
        base = 1001;
        
        n = (int)s.size();
        hash.assign(n+1, 0);
        pow.assign(n+1, 1);
        
        for(int i=0; i<n; i++){
            hash[i+1] = calc_mod(mul(hash[i], base) + s[i]);
            pow[i+1] = calc_mod(mul(pow[i], base));
        }
    }

    ull calc_mod(ull x){
        ull xu = x >> 61;
        ull xd = x & MASK61;
        ull res = xu + xd;
        if(res >= mod) res -= mod;
        return res;
    }

    ull mul(ull a, ull b){
        ull au = a >> 31;
        ull ad = a & MASK31;
        ull bu = b >> 31;
        ull bd = b & MASK31;
        ull mid = ad * bu + au * bd;
        ull midu = mid >> 30;
        ull midd = mid & MASK30;
        return calc_mod(au * bu * 2 + midu + (midd << 31) + ad * bd);
    }

    //[l,r)のハッシュ値
    inline ull get(int l, int r){
        ull res = calc_mod(hash[r] + mod*3-mul(hash[l], pow[r-l]));
        return res;
    }
    //string tのハッシュ値
    inline ull get(string t){
        ull res = 0;
        for(int i=0; i<t.size(); i++){
            res = calc_mod(mul(res, base)+t[i]);
        }
        return res;
    }
    //string s中のtの数をカウント
    inline int count(string t) {
        if(t.size() > n) return 0;
        auto hs = get(t);
        int res = 0;
        for(int i=0; i<n-t.size()+1; i++){
            if(get(i, i+t.size()) == hs) res++; 
        }
        return res;
    }

    /* 
        concat 
        @verify https://codeforces.com/problemset/problem/514/C
    */
    inline ull concat(ull h1, ull h2, int h2len){
      return calc_mod(h2 + mul(h1, pow[h2len]));
    }

    // LCPを求める S[a:] T[b:]
    inline int LCP(int a, int b){
        int len = min((int)hash.size()-a, (int)hash.size()-b);
        
        int lb = -1, ub = len;
        while(ub-lb>1){
            int mid = (lb+ub)/2;

            if(get(a, a+mid) == get(b, b+mid)) lb = mid;
            else ub = mid;
        }
        return lb;
    }
};
int maximum_independent_set(vector<vector<int>> &g) {
  int n = g.size();
  int n1 = n/2, n2 = n-n1;
  vector<int> dp2((1<<n2));
  REP(i,n2) dp2[(1<<i)] = 1;
  REP(bit, (1<<n2)) {
    REP(i,n2) {
      if(bit >> i & 1) continue;
      bool ok = true;
      REP(j,n2) {
        if(bit >> j & 1) ok &= g[n1+i][n1+j];
      }
      int c = 0;
      if(ok) c++;
      dp2[bit | (1 << i)] = max(dp2[bit | (1 << i)], dp2[bit] + c);
    }
  }
  int ans = 0;
  REP(bit,(1<<n1)) {
    vector<int> cand;
    REP(i,n1) {
      if(bit >> i & 1) cand.push_back(i);
    }
    bool ok = true;
    REP(i,cand.size()) {
      FOR(j, i+1 ,cand.size()) {
        ok &= g[cand[i]][cand[j]];
      }
    }
    if(!ok) continue;
    ll bit2 = 0;
    REP(i,n2) {
      ok = true;
      REP(j,cand.size()){
        ok &= g[i+n1][cand[j]];
      }
      if(ok) bit2 |= (1<<i);
    }
    ans = max(ans, __builtin_popcount(bit) + dp2[bit2]);
  }
  return ans;
}

int main() {  
  cin.tie(0);
  ios::sync_with_stdio(false);
  cout << fixed << setprecision(12);
  
  ll N; cin >> N;
  vector<ll> d;
  ll t = N;
  for(ll i=1; i*i<=t; i++) {
    if(t%i == 0) {
      d.push_back(i);
      if(t/i != i) d.push_back(t/i);
    }
  }
  sort(all(d));
  map<ll, int> mp;
  for(ll i=2; i*i<=t; i++) {
    if(t%i == 0) {
      while(t%i == 0) {
        mp[i]++;
        t/=i;
      }
    }
  }
  if(t != 1) mp[t]++;
  vector<ll> v;
  for(auto e: mp) {
    ll tmp = 1;
    REP(i,e.second) tmp *= e.first;
    v.push_back(tmp);
  } 
  Combination<modint> comb(10010);
  int n = mp.size();
  modint ans = 0;
  REP(bit, (1<<n)) {
    ll tmp = 1;
    int cnt = 0;
    REP(i,d.size()) {
      bool f = true;
      REP(j,n) {
        if(bit >> j & 1) {
          if(d[i]%v[j] == 0) f = false;
        }
      }
      if(f) cnt++;
    }
    
    modint res = 0;
    for(int i=1; i<=cnt; i++) res += comb.P(cnt, i);
    if(__builtin_popcount(bit)%2 == 1) res *= -1;
    ans += res;
  }
  cout << ans << endl;
  return 0;
}
accuracy: 1
time_ms: 110
memory_kb: 3580
final_rank: 4

code_snippet: #include <bits/stdc++.h>
//#include <atcoder/all>
//using namespace atcoder;
#pragma GCC target ("avx2")
#pragma GCC optimization ("O3")
#pragma GCC optimization ("unroll-loops")
using namespace std;
 
typedef vector<int> VI;
typedef vector<VI> VVI;
typedef vector<string> VS;
typedef pair<int, int> PII;
typedef pair<int, int> pii;
typedef pair<long long, long long> PLL;
typedef pair<int, PII> TIII;
 
typedef long long ll;
typedef long double ld;
typedef unsigned long long ull;
 
 
#define FOR(i, s, n) for (int i = s; i < (int)n; ++i)
#define REP(i, n) FOR(i, 0, n)
#define rep(i, a, b) for (int i = a; i < (b); ++i)
#define trav(a, x) for (auto &a : x)
#define all(x) x.begin(), x.end()
 
#define MOD 1000000007
 
template<class T1, class T2> inline bool chmax(T1 &a, T2 b) {if (a < b) {a = b; return true;} return false;}
template<class T1, class T2> inline bool chmin(T1 &a, T2 b) {if (a > b) {a = b; return true;} return false;}
const double EPS = 1e-8, PI = acos(-1);
const double pi = 3.141592653589793238462643383279;
//ここから編集    
typedef string::const_iterator State;
ll GCD(ll a, ll b){
  return (b==0)?a:GCD(b, a%b);
}
ll LCM(ll a, ll b){
  return a/GCD(a, b) * b;
}
template< int mod >
struct ModInt {
  int x;
 
  ModInt() : x(0) {}
 
  ModInt(int64_t y) : x(y >= 0 ? y % mod : (mod - (-y) % mod) % mod) {}
 
  ModInt &operator+=(const ModInt &p) {
    if((x += p.x) >= mod) x -= mod;
    return *this;
  }
 
  ModInt &operator-=(const ModInt &p) {
    if((x += mod - p.x) >= mod) x -= mod;
    return *this;
  }
 
  ModInt &operator*=(const ModInt &p) {
    x = (int) (1LL * x * p.x % mod);
    return *this;
  }
 
  ModInt &operator/=(const ModInt &p) {
    *this *= p.inverse();
    return *this;
  }
 
  ModInt operator-() const { return ModInt(-x); }
 
  ModInt operator+(const ModInt &p) const { return ModInt(*this) += p; }
 
  ModInt operator-(const ModInt &p) const { return ModInt(*this) -= p; }
 
  ModInt operator*(const ModInt &p) const { return ModInt(*this) *= p; }
 
  ModInt operator/(const ModInt &p) const { return ModInt(*this) /= p; }
 
  bool operator==(const ModInt &p) const { return x == p.x; }
 
  bool operator!=(const ModInt &p) const { return x != p.x; }
 
  ModInt inverse() const {
    int a = x, b = mod, u = 1, v = 0, t;
    while(b > 0) {
      t = a / b;
      swap(a -= t * b, b);
      swap(u -= t * v, v);
    }
    return ModInt(u);
  }
 
  ModInt pow(int64_t n) const {
    ModInt ret(1), mul(x);
    while(n > 0) {
      if(n & 1) ret *= mul;
      mul *= mul;
      n >>= 1;
    }
    return ret;
  }
 
  friend ostream &operator<<(ostream &os, const ModInt &p) {
    return os << p.x;
  }
 
  friend istream &operator>>(istream &is, ModInt &a) {
    int64_t t;
    is >> t;
    a = ModInt< mod >(t);
    return (is);
  }
 
  static int get_mod() { return mod; }
};
 
using modint = ModInt< 1000000007 >;
template< typename T >
struct Combination {
  vector< T > _fact, _rfact, _inv;
 
  Combination(int sz) : _fact(sz + 1), _rfact(sz + 1), _inv(sz + 1) {
    _fact[0] = _rfact[sz] = _inv[0] = 1;
    for(int i = 1; i <= sz; i++) _fact[i] = _fact[i - 1] * i;
    _rfact[sz] /= _fact[sz];
    for(int i = sz - 1; i >= 0; i--) _rfact[i] = _rfact[i + 1] * (i + 1);
    for(int i = 1; i <= sz; i++) _inv[i] = _rfact[i] * _fact[i - 1];
  }
 
  inline T fact(int k) const { return _fact[k]; }
 
  inline T rfact(int k) const { return _rfact[k]; }
 
  inline T inv(int k) const { return _inv[k]; }
 
  T P(int n, int r) const {
    if(r < 0 || n < r) return 0;
    return fact(n) * rfact(n - r);
  }
 
  T C(int p, int q) const {
    if(q < 0 || p < q) return 0;
    return fact(p) * rfact(q) * rfact(p - q);
  }
 
  T H(int n, int r) const {
    if(n < 0 || r < 0) return (0);
    return r == 0 ? 1 : C(n + r - 1, r);
  }
};
 
ll modpow(ll x, ll n, ll mod) {
  ll res = 1;
  x %= mod;
  if(x == 0) return 0;
  while(n) {
    if(n&1) res = (res * x) % mod;
    x = (x * x) % mod;
    n >>= 1;
  }
  return res;
} 
inline long long mod(long long a, long long m) {
    return (a % m + m) % m;
}
template<typename T> 
struct BIT{
  int N;
  std::vector<T> node;
  BIT(){}
  BIT(int n){
    N = n;
    node.resize(N+10);
  }
  void build(int n) {
    N = n;
    node.resize(N+10);
  }
  /* a: 1-indexed */
  void add(int a, T x){
    for(int i=a; i<(int)node.size(); i += i & -i) node[i] += x;
  }

  /* [1, a] */
  T sum(int a){
    T res = 0;
    for(int x=a; x>0; x -= x & -x) res += node[x];
    return res;
  }

  /* [l, r] */
  T rangesum(int l, int r){
    return sum(r) - sum(l-1);
  }

  /* 
    a1+a2+...+aw >= valとなるような最小のwを返す
    @verify https://codeforces.com/contest/992/problem/E
  */
  int lower_bound(T val) {
    if(val < 0) return 0;

    int res = 0;
    int n = 1; 
    while (n < N) n *= 2;

    T tv=0;
    for (int k = n; k > 0; k /= 2) {
      if(res + k < N && node[res + k] < val){
        val -= node[res+k];
        res += k;
      }
    }
    return res+1; 
  }
};
struct UnionFind{
  std::vector<int> par;
  std::vector<int> siz;

  UnionFind(int sz_): par(sz_), siz(sz_) {
    for(int i=0; i<sz_; ++i) par[i] = i, siz[i] = 1;
  }

  void init(int sz_){
    par.resize(sz_);
    siz.resize(sz_);
    for(int i=0; i<sz_; ++i) par[i] = i, siz[i] = 1;
  }

  int root(int x){
    if(x == par[x]) return x;
    return par[x] = root(par[x]);
  }

  bool merge(int x, int y){
    x = root(x), y = root(y);
    if(x == y) return false;
    if(siz[x] < siz[y]) std::swap(x, y);
    siz[x] += siz[y];
    par[y] = x;
    return true;
  }

  bool issame(int x, int y){
    return root(x) == root(y);
  }

  int size(int x){
    return siz[root(x)];
  }
};
struct RollingHash{

    using ull = unsigned long long;
    const ull mod = (1ULL << 61) - 1;
    const ull MASK30 = (1ULL << 30) - 1;
    const ull MASK31 = (1ULL << 31) - 1;

    const ull MASK61 = mod;

    ull base;
    int n;
    vector<ull> hash, pow;

    RollingHash(const string &s)
    {
        random_device rnd;
        mt19937_64 mt(rnd());
        base = 1001;
        
        n = (int)s.size();
        hash.assign(n+1, 0);
        pow.assign(n+1, 1);
        
        for(int i=0; i<n; i++){
            hash[i+1] = calc_mod(mul(hash[i], base) + s[i]);
            pow[i+1] = calc_mod(mul(pow[i], base));
        }
    }

    ull calc_mod(ull x){
        ull xu = x >> 61;
        ull xd = x & MASK61;
        ull res = xu + xd;
        if(res >= mod) res -= mod;
        return res;
    }

    ull mul(ull a, ull b){
        ull au = a >> 31;
        ull ad = a & MASK31;
        ull bu = b >> 31;
        ull bd = b & MASK31;
        ull mid = ad * bu + au * bd;
        ull midu = mid >> 30;
        ull midd = mid & MASK30;
        return calc_mod(au * bu * 2 + midu + (midd << 31) + ad * bd);
    }

    //[l,r)のハッシュ値
    inline ull get(int l, int r){
        ull res = calc_mod(hash[r] + mod*3-mul(hash[l], pow[r-l]));
        return res;
    }
    //string tのハッシュ値
    inline ull get(string t){
        ull res = 0;
        for(int i=0; i<t.size(); i++){
            res = calc_mod(mul(res, base)+t[i]);
        }
        return res;
    }
    //string s中のtの数をカウント
    inline int count(string t) {
        if(t.size() > n) return 0;
        auto hs = get(t);
        int res = 0;
        for(int i=0; i<n-t.size()+1; i++){
            if(get(i, i+t.size()) == hs) res++; 
        }
        return res;
    }

    /* 
        concat 
        @verify https://codeforces.com/problemset/problem/514/C
    */
    inline ull concat(ull h1, ull h2, int h2len){
      return calc_mod(h2 + mul(h1, pow[h2len]));
    }

    // LCPを求める S[a:] T[b:]
    inline int LCP(int a, int b){
        int len = min((int)hash.size()-a, (int)hash.size()-b);
        
        int lb = -1, ub = len;
        while(ub-lb>1){
            int mid = (lb+ub)/2;

            if(get(a, a+mid) == get(b, b+mid)) lb = mid;
            else ub = mid;
        }
        return lb;
    }
};
int maximum_independent_set(vector<vector<int>> &g) {
  int n = g.size();
  int n1 = n/2, n2 = n-n1;
  vector<int> dp2((1<<n2));
  REP(i,n2) dp2[(1<<i)] = 1;
  REP(bit, (1<<n2)) {
    REP(i,n2) {
      if(bit >> i & 1) continue;
      bool ok = true;
      REP(j,n2) {
        if(bit >> j & 1) ok &= g[n1+i][n1+j];
      }
      int c = 0;
      if(ok) c++;
      dp2[bit | (1 << i)] = max(dp2[bit | (1 << i)], dp2[bit] + c);
    }
  }
  int ans = 0;
  REP(bit,(1<<n1)) {
    vector<int> cand;
    REP(i,n1) {
      if(bit >> i & 1) cand.push_back(i);
    }
    bool ok = true;
    REP(i,cand.size()) {
      FOR(j, i+1 ,cand.size()) {
        ok &= g[cand[i]][cand[j]];
      }
    }
    if(!ok) continue;
    ll bit2 = 0;
    REP(i,n2) {
      ok = true;
      REP(j,cand.size()){
        ok &= g[i+n1][cand[j]];
      }
      if(ok) bit2 |= (1<<i);
    }
    ans = max(ans, __builtin_popcount(bit) + dp2[bit2]);
  }
  return ans;
}

int main() {  
  cin.tie(0);
  ios::sync_with_stdio(false);
  cout << fixed << setprecision(12);
  
  ll N; cin >> N;
  vector<ll> d;
  ll t = N;
  for(ll i=1; i*i<=t; i++) {
    if(t%i == 0) {
      d.push_back(i);
      if(t/i != i) d.push_back(t/i);
    }
  }
  sort(all(d));
  map<ll, int> mp;
  for(ll i=2; i*i<=t; i++) {
    if(t%i == 0) {
      while(t%i == 0) {
        mp[i]++;
        t/=i;
      }
    }
  }
  if(t != 1) mp[t]++;
  vector<ll> v;
  for(auto e: mp) {
    ll tmp = 1;
    REP(i,e.second) tmp *= e.first;
    v.push_back(tmp);
  } 
  Combination<modint> comb(2010);
  int n = mp.size();
  modint ans = 0;
  REP(bit, (1<<n)) {
    ll tmp = 1;
    int cnt = 0;
    REP(i,d.size()) {
      bool f = true;
      REP(j,n) {
        if(bit >> j & 1) {
          if(d[i]%v[j] == 0) f = false;
        }
      }
      if(f) cnt++;
    }
    
    modint res = 0;
    for(int i=1; i<=cnt; i++) res += comb.P(cnt, i);
    if(__builtin_popcount(bit)%2 == 1) res *= -1;
    ans += res;
  }
  cout << ans << endl;
  return 0;
}
accuracy: 0.696969696969697
time_ms: 110
memory_kb: 3484
final_rank: 14

code_snippet: #include<bits/stdc++.h>
typedef long long int ll;
typedef unsigned long long int ull;
#define BIG_NUM 2000000000
#define HUGE_NUM 4000000000000000000 //オーバーフローに注意
#define MOD 1000000007
#define EPS 0.000000001
using namespace std;



#define SIZE 3000005
#define MAX 25


ll POW[MAX];
ll fact[SIZE],inv_fact[SIZE];

ll mod_pow(ll x,ll count, ll mod){

	if(count == 0)return 1;
	ll ret = mod_pow((x*x)%mod,count/2,mod);
	if(count%2 == 1){

		ret = (ret*x)%mod;
	}
	return ret;
}

ll extgcd(ll a,ll b,ll &x,ll &y){
	ll d = a;
	if(b != 0){
		d = extgcd(b,a%b,y,x);
		y -= (a/b)*x;
	}else{
		x = 1;
		y = 0;
	}
	return d;
}

ll mod_inverse(ll a,ll m){
    ll x,y;
    extgcd(a,m,x,y);
    return (m+x%m)%m;
}

ll nCk(ll n,ll k){

	if(k > n)return 0;

	ll ret = fact[n]*inv_fact[k];
	ret %= MOD;
	ret *= inv_fact[n-k];

	return ret%MOD;
}

ll nPk(ll n,ll k){

	if(k > n)return 0;

	ll ret = fact[n]*inv_fact[n-k];

	return ret%MOD;
}



int main(){

	fact[0] = 1;
	for(ll i = 1; i < SIZE; i++){
		fact[i] = i*fact[i-1];
		fact[i] %= MOD;
	}
	inv_fact[SIZE-1] = mod_inverse(fact[SIZE-1],MOD);
	for(ll i = SIZE-1; i >= 1; i--){

		inv_fact[i-1] = inv_fact[i]*i;
		inv_fact[i-1] %= MOD;
	}
	for(ll i = 1; i < SIZE; i++){

		inv_fact[i] += inv_fact[i-1];
		inv_fact[i] %= MOD;
	}

	POW[0] = 1;
	for(int i = 1; i < MAX; i++){

		POW[i] = POW[i-1]*2;
	}

	ll N;
	scanf("%lld",&N);

	ll tmp = N;
	vector<ll> vec;

	for(ll i = 2; i*i <= N; i++){
		if(tmp%i != 0)continue;

		ll count = 0;

		while(tmp%i == 0){

			tmp /= i;
			count++;
		}
		vec.push_back(count);
	}
	if(tmp > 1){

		vec.push_back(1);
	}

	ll ans = 0;

	for(ll state = 0; state < POW[vec.size()]; state++){
		ll mult = 1;
		ll count = 0;
		for(ll loop = 0; loop < vec.size(); loop++){
			if(state & POW[loop]){ //最大次数に到達しない


				mult *= vec[loop];
				count++;

			}else{

				mult *= vec[loop]+1;
			}
		}

		//printf("state:%lld mult:%lld\n",state,mult);

		ll base = fact[mult];
		base *= inv_fact[mult-1];
		base %= MOD;

		if(count%2 == 1){

			ans -= base;
			if(ans < 0){

				ans += MOD;
			}
		}else{

			ans += base;
			ans %= MOD;
		}
	}

	printf("%lld\n",ans);

	return 0;
}
accuracy: 1
time_ms: 40
memory_kb: 50160
final_rank: 5

code_snippet: #include<bits/stdc++.h>
typedef long long int ll;
typedef unsigned long long int ull;
#define BIG_NUM 2000000000
#define HUGE_NUM 9223372036854775807
#define MOD 1000000007
#define EPS 0.000000001
using namespace std;


#define SIZE 5000005
#define MAX 25


ll fact[SIZE],inv_fact[SIZE];
ll POW[MAX+1];


ll mod_pow(ll x,ll count, ll mod){

	if(count == 0)return 1;
	ll ret = mod_pow((x*x)%mod,count/2,mod);
	if(count%2 == 1){

		ret = (ret*x)%mod;
	}
	return ret;
}

ll extgcd(ll a,ll b,ll &x,ll &y){
	ll d = a;
	if(b != 0){
		d = extgcd(b,a%b,y,x);
		y -= (a/b)*x;
	}else{
		x = 1;
		y = 0;
	}
	return d;
}

ll mod_inverse(ll a,ll m){
    ll x,y;
    extgcd(a,m,x,y);
    return (m+x%m)%m;
}

ll nCk(ll n,ll k){

	if(k > n)return 0;

	ll ret = fact[n]*inv_fact[k];
	ret %= MOD;
	ret *= inv_fact[n-k];

	return ret%MOD;
}

//https://betrue12.hateblo.jp/entry/2020/11/03/205320

int main(){

	fact[0] = 1;
	for(ll i = 1; i < SIZE; i++){
		fact[i] = i*fact[i-1];
		fact[i] %= MOD;
	}
	inv_fact[SIZE-1] = mod_inverse(fact[SIZE-1],MOD);
	for(ll i = SIZE-1; i >= 1; i--){

		inv_fact[i-1] = inv_fact[i]*i;
		inv_fact[i-1] %= MOD;
	}
	for(ll i = 1; i < SIZE; i++){

		inv_fact[i] += inv_fact[i-1];
		inv_fact[i] %= MOD;
	}

	POW[0] = 1;
	for(int i = 1; i <= MAX; i++){

		POW[i] = POW[i-1]*2;
	}

	vector<ll> V;

	ll N;
	scanf("%lld",&N);

	ll tmp = N;

	for(ll i = 2; i*i <= N; i++){
		if(tmp%i != 0)continue;

		ll count = 0;

		while(tmp%i == 0){
			count++;
			tmp /= i;
		}
		V.push_back(count);
	}

	if(tmp > 1)V.push_back(1);

	ll ans = 0;

	for(ll state = 0; state < POW[V.size()]; state++){

		ll mult = 1;
		ll count = 0;

		for(ll loop = 0; loop < V.size(); loop++){
			if(state&POW[loop]){

				mult *= V[loop];
				mult %= MOD;
				count++;

			}else{

				mult *= (V[loop]+1);
				mult %= MOD;
			}
		}

		tmp = fact[mult]*inv_fact[(mult-1)];
		tmp %= MOD;

		if(count%2 == 0){

			ans += tmp;
			ans %= MOD;
		}else{

			ans -= tmp;
			if(ans < 0){

				ans += MOD;
			}
		}
	}

	printf("%lld\n",ans);

	return 0;
}
accuracy: 1
time_ms: 70
memory_kb: 81412
final_rank: 7

code_snippet: #include<bits/stdc++.h>
typedef long long int ll;
typedef unsigned long long int ull;
#define BIG_NUM 2000000000
#define HUGE_NUM 9223372036854775807
#define MOD 1000000007
#define EPS 0.000000001
using namespace std;


#define SIZE 2000005
#define MAX 24

ll POW[25];
ll fact[SIZE],inv_fact[SIZE];

ll mod_pow(ll x,ll count, ll mod){

	if(count == 0)return 1;
	ll ret = mod_pow((x*x)%mod,count/2,mod);
	if(count%2 == 1){

		ret = (ret*x)%mod;
	}
	return ret;
}

ll extgcd(ll a,ll b,ll &x,ll &y){
	ll d = a;
	if(b != 0){
		d = extgcd(b,a%b,y,x);
		y -= (a/b)*x;
	}else{
		x = 1;
		y = 0;
	}
	return d;
}

ll mod_inverse(ll a,ll m){
    ll x,y;
    extgcd(a,m,x,y);
    return (m+x%m)%m;
}

ll nCk(ll n,ll k){

	if(k > n)return 0;

	ll ret = fact[n]*inv_fact[k];
	ret %= MOD;
	ret *= inv_fact[n-k];

	return ret%MOD;
}

//ありがとうございました
//https://betrue12.hateblo.jp/entry/2020/11/03/205320

int main(){

	POW[0] = 1;
	for(int i = 1; i <= MAX; i++){

		POW[i] = POW[i-1]*2;
	}

	fact[0] = 1;
	for(ll i = 1; i < SIZE; i++){
		fact[i] = i*fact[i-1];
		fact[i] %= MOD;
	}
	inv_fact[SIZE-1] = mod_inverse(fact[SIZE-1],MOD);
	for(ll i = SIZE-1; i >= 1; i--){

		inv_fact[i-1] = inv_fact[i]*i;
		inv_fact[i-1] %= MOD;
	}
	for(ll i = 1; i < SIZE; i++){

		inv_fact[i] += inv_fact[i-1]; //★★累積和にする★★
		inv_fact[i] %= MOD;
	}

	ll N;
	scanf("%lld",&N);

	vector<ll> vec;

	ll tmp = N;
	for(ll i = 2; i*i <= N; i++){
		if(tmp%i != 0)continue;

		ll count = 0;
		while(tmp%i == 0){
			tmp /= i;
			count++;
		}
		vec.push_back(count);
	}
	if(tmp > 1)vec.push_back(1);

	ll num = vec.size();
	ll ans = 0;

	for(ll state = 0; state < POW[num]; state++){
		ll count = 0;
		ll mult = 1;
		for(ll loop = 0; loop < num; loop++){
			if(state & POW[loop]){

				mult *= vec[loop];
				count++;
			}else{

				mult *= vec[loop]+1;
			}
		}

		ll tmp = fact[mult];
		tmp *= inv_fact[mult-1];
		tmp %= MOD;

		if(count%2 == 1){

			ans -= tmp;
			if(ans < 0){
				ans += MOD;
			}

		}else{

			ans += tmp;
			ans %= MOD;
		}
	}

	printf("%lld\n",ans);
	return 0;
}
accuracy: 1
time_ms: 30
memory_kb: 34524
final_rank: 3

code_snippet: // clang-format off
#include <bits/stdc++.h>
using namespace std;
using ll = long long;
#define rep(i,n) for(int i=0;i<(int)(n);++i)
#define all(x) (x).begin(),(x).end()
#define pb push_back
#define fi first
#define se second
#define dbg(x) cout<<#x" = "<<((x))<<endl
template<class T,class U> ostream& operator<<(ostream& o, const pair<T,U> &p){o<<"("<<p.fi<<","<<p.se<<")";return o;}
template<class T> ostream& operator<<(ostream& o, const vector<T> &v){o<<"[";for(T t:v){o<<t<<",";}o<<"]";return o;}
// clang-format on

template <int mod>
struct ModInt {
    int x;

    ModInt() : x(0) {}
    ModInt(int64_t y) : x(y >= 0 ? y % mod : (mod - (-y) % mod) % mod) {}

    ModInt &operator+=(const ModInt &p) {
        if ((x += p.x) >= mod) x -= mod;
        return *this;
    }
    ModInt &operator-=(const ModInt &p) {
        if ((x += mod - p.x) >= mod) x -= mod;
        return *this;
    }
    ModInt &operator*=(const ModInt &p) {
        x = (int)(1LL * x * p.x % mod);
        return *this;
    }
    ModInt &operator/=(const ModInt &p) {
        *this *= p.inverse();
        return *this;
    }

    ModInt operator-() const { return ModInt(-x); }
    ModInt operator+(const ModInt &p) const { return ModInt(*this) += p; }
    ModInt operator-(const ModInt &p) const { return ModInt(*this) -= p; }
    ModInt operator*(const ModInt &p) const { return ModInt(*this) *= p; }
    ModInt operator/(const ModInt &p) const { return ModInt(*this) /= p; }
    bool operator==(const ModInt &p) const { return x == p.x; }
    bool operator!=(const ModInt &p) const { return x != p.x; }

    ModInt inverse() const {
        int a = x, b = mod, u = 1, v = 0, t;
        while (b > 0) {
            t = a / b;
            swap(a -= t * b, b);
            swap(u -= t * v, v);
        }
        return ModInt(u);
    }

    ModInt pow(int64_t n) const {
        ModInt ret(1), mul(x);
        while (n > 0) {
            if (n & 1) ret *= mul;
            mul *= mul;
            n >>= 1;
        }
        return ret;
    }

    friend ostream &operator<<(ostream &os, const ModInt &p) {
        return os << p.x;
    }

    friend istream &operator>>(istream &is, ModInt &a) {
        int64_t t;
        is >> t;
        a = ModInt<mod>(t);
        return (is);
    }

    static int get_mod() { return mod; }
};

const int mod = 1e9 + 7;
using mint = ModInt<mod>;

// for test
// 200560490130
// 963761198400

const int N = 7000;
mint fact[N], inv_fact[N];
mint C(int n, int r) {
    if (n < r) return 0;
    return fact[n] * inv_fact[r] * inv_fact[n - r];
}

int main() {
    fact[0] = 1;
    for (int i = 1; i < N; ++i) fact[i] = fact[i - 1] * i;
    inv_fact[N - 1] = fact[N - 1].inverse();
    for (int i = N - 2; i >= 0; --i) inv_fact[i] = inv_fact[i + 1] * (i + 1);

    ll n;
    cin >> n;

    map<ll, int> f;
    vector<ll> d({1, n});

    ll t = n;
    for (ll i = 2; i * i <= n; ++i) {
        if (n % i == 0) {
            d.pb(i);
            d.pb(n / i);
        }
        while (t % i == 0) {
            ++f[i];
            t /= i;
        }
    }
    if (t > 1) ++f[t];
    sort(all(d));
    d.erase(unique(all(d)), d.end());
    int D = d.size();

    int F = f.size();
    vector<ll> x;
    vector<int> num;
    for (const auto &p : f) {
        x.pb(p.fi);
        num.pb(p.se);
    }

    vector<int> cand(1 << F);
    rep(i, D) {
        int cv = 0;
        ll xx = d[i];
        rep(j, F) {
            int ct = 0;
            while (xx % x[j] == 0) {
                ++ct;
                xx /= x[j];
            }
            if (ct == num[j]) cv |= (1 << j);
        }
        ++cand[cv];
    }
    rep(i, F) {
        rep(mask, 1 << F) {
            if (mask & (1 << i)) cand[mask] += cand[mask ^ (1 << i)];
        }
    }

    mint ans = 0;
    for (int i = 1; i <= D; ++i) {
        mint pat = 0;
        rep(mask, 1 << F) {
            int mul = 1;
            if ((F - __builtin_popcount(mask)) % 2) mul = -1;
            pat += C(cand[mask], i) * mul;
        }
        ans += pat * fact[i];
    }
    cout << ans << "\n";
    return 0;
}
accuracy: 1
time_ms: 30
memory_kb: 3332
final_rank: 2

code_snippet: #include<bits/stdc++.h>
using namespace std;
#define N (1000000000+7)
//#define N 998244353
#define INF 1e16
typedef long long ll;
typedef pair<int,int> P;
typedef pair<int,P> Q;
typedef vector<ll> vec;
typedef vector<vec> mat;
const int inf = (int)1e9; 
 
ll gcd(ll a, ll b) {
	if (b > a) {
		ll tmp = b;
		b = a;
		a = tmp;
	}
	if (a%b == 0)return b;
	else return gcd(b, a%b);
}

ll kaijo[2000010];
ll sum[2000010];
void init() {
	kaijo[0] = 1;
	for (ll i = 1;i < 2000010;i++)kaijo[i] = (kaijo[i - 1] * i) % N;
}
 
ll inv(ll x,ll power) {
	ll res = 1;
	ll k = power;
	ll y = x%N;
	while (k) {
		if (k & 1)res = (res*y) % N;
		y = (y%N*y%N) % N;
		k /= 2;
	}
	return res;
}

void init1(){
	sum[0] = 1;
	for(ll i=1;i< 2000010;i++){
		sum[i] = (sum[i-1]+inv(kaijo[i],N-2))%N;
	}
}

ll Pow(ll x,ll power,ll r){
	ll res = 1;
	ll k = power;
	ll y = x%r;
	while (k) {
		if (k & 1)res = (res*y) % r;
		y = (y%r*y%N) % r;
		k /= 2;
	}
	return res;
}

ll Comb(ll n, ll k) {
	if (n < 0 || k < 0 || (n - k) < 0)return 0;
	ll b = kaijo[n];
	ll c = kaijo[n - k];
	ll d = kaijo[k];
	ll cd = (c*d) % N;
	return ((b%N)*(inv(cd,N-2)) % N) % N;
}
 
ll itertive_pow(ll x,ll power) {
	ll res = 1;
	ll k = power;
	ll y = x;
	while (k) {
		if (k & 1)res = (res*y) ;
		y = y*y;
		k /= 2;
	}
	return res;
}


map<ll,ll>mp1,mp2;

void precalc(ll n){
	vector<ll>prime;
	ll p = n;
	for(ll i=2;i*i<=n;i++){
		if(p%i==0){
			while(p%i==0)p/=i;
			prime.push_back(i);
		}
	}
	if(p>1)prime.push_back(p);
	ll m = prime.size();
	mp1[1]=1;
	mp2[1]=1;
	for(ll i=1;i<(1LL<<m);i++){
		ll cnt = 0;
		ll d = 1;
		for(ll j=0;j<m;j++){
			if((i>>j)&1){
				d*=prime[j];
				cnt++;
			}
		}
		mp1[d] = ((cnt%2==0)?1:-1);
	}
}



int main(void){
	ll n;
	cin>>n;
	ll ans = 0;
	sum[0] = 0;
	init();
	init1();
	precalc(n);
	for(auto [d,cnt]:mp1){
		ll x = n/d;
		ll c = 0;
		for(ll i=1;i*i<=x;i++){
			if(x%i==0){
				ll t = x/i;
				if(i==t)c++;
				else c+=2LL;
			}
		}
		ll tmp = (kaijo[c]*sum[c-1])%N;
		tmp = (mp1[d]*tmp+N)%N;
		tmp = (tmp+N)%N;
		ans = (ans+tmp+N)%N;
	}
	cout<<ans<<endl;
	return 0;
}
accuracy: 1
time_ms: 290
memory_kb: 34732
final_rank: 12

code_snippet: #include <bits/stdc++.h>
using namespace std;
typedef long long ll;
#define rep(i, srt, end) for (long long i = (srt); i < (long long)(end); i++)

vector<ll> yakusu(ll n){
    vector<ll> ret;
    for(ll i = 1; i*i <= n; i++){
        if(n % i != 0) continue;
        ret.push_back(i);
        if(i*i != n) ret.push_back(n/i);
    }
    sort(ret.begin(), ret.end());
    reverse(ret.begin(), ret.end());
    return ret;
}

const ll mod = 1000000000 + 7;
#define NMAX 1000010
ll fac[NMAX], inv[NMAX];

ll mod_pow(ll a, ll n, ll mod){
    ll ret = 1;
    while(n > 0){
        if(n & 1) ret = (ret*(a % mod))%mod;
        a = ((a%mod)*(a%mod)) % mod;
        n = n >> 1;
    }
    return ret;
}

ll mod_inv(ll a, ll mod){
    return mod_pow(a, mod-2, mod);
}

void mae_nck(){
    fac[1] = 1;
    inv[1] = 1;
    for(ll i = 2; i < NMAX; i++){
        fac[i] = (fac[i-1] * i)%mod;
        inv[i] = (inv[i-1] * mod_inv(i, mod))%mod;
    }
}

ll mod_nck(ll n, ll k){
    if (n < k) return 0;
    if (n < 0 || k < 0) return 0;
    if(k == 0 || k == n) return 1;
    ll ret = ((fac[n] * inv[k])%mod * inv[n-k])%mod;
    return ret;
}

ll calc(ll n) {
    ll res = 0;
    for(ll i = 1; i <= n; i++) {
        res += (mod_nck(n, i) * fac[i]) % mod;
        res %= mod; 
    }
    return res;
}

int main() {
    mae_nck();
    ll n;
    cin >> n;
    ll invalid = 0;
    auto vn = yakusu(n);
    map<ll, ll> cnt;
    for(auto e : vn) {
        if(cnt[e] == 1 || e == n) continue;
        auto v = yakusu(e);
        if(cnt[e] == 0) {
            invalid += calc(v.size());
            invalid %= mod;
            for(auto p : v) cnt[p]++;
        } else {
            invalid -= ((cnt[e] - 1) * calc(v.size())) % mod;
            invalid %= mod;
            ll gap = cnt[e] - 1;
            for(auto p : v) cnt[p] -= gap;    
        }
    }
    ll sum = calc(vn.size());
    ll ans = sum - invalid + mod;
    ans %= mod;
    cout << ans << endl;
    return 0;
}
accuracy: 1
time_ms: 290
memory_kb: 19408
final_rank: 8

code_snippet: #include <bits/stdc++.h>
using namespace std;
typedef long long ll;
#define rep(i, srt, end) for (long long i = (srt); i < (long long)(end); i++)

vector<ll> yakusu(ll n){
    vector<ll> ret;
    for(ll i = 1; i*i <= n; i++){
        if(n % i != 0) continue;
        ret.push_back(i);
        if(i*i != n) ret.push_back(n/i);
    }
    sort(ret.begin(), ret.end());
    reverse(ret.begin(), ret.end());
    return ret;
}

const ll mod = 1000000000 + 7;
#define NMAX 1000010
ll fac[NMAX], inv[NMAX];

ll mod_pow(ll a, ll n, ll mod){
    ll ret = 1;
    while(n > 0){
        if(n & 1) ret = (ret*(a % mod))%mod;
        a = ((a%mod)*(a%mod)) % mod;
        n = n >> 1;
    }
    return ret;
}

ll mod_inv(ll a, ll mod){
    return mod_pow(a, mod-2, mod);
}

void mae_nck(){
    fac[1] = 1;
    inv[1] = 1;
    for(ll i = 2; i < NMAX; i++){
        fac[i] = (fac[i-1] * i)%mod;
        inv[i] = (inv[i-1] * mod_inv(i, mod))%mod;
    }
}

ll mod_nck(ll n, ll k){
    if (n < k) return 0;
    if (n < 0 || k < 0) return 0;
    if(k == 0 || k == n) return 1;
    ll ret = ((fac[n] * inv[k])%mod * inv[n-k])%mod;
    return ret;
}

ll calc(ll n) {
    ll res = 0;
    for(ll i = 1; i <= n; i++) {
        res += (mod_nck(n, i) * fac[i]) % mod;
        res %= mod; 
    }
    return res;
}

int main() {
    mae_nck();
    ll n;
    cin >> n;
    ll invalid = 0;
    auto vn = yakusu(n);
    map<ll, ll> cnt;
    for(auto e : vn) {
        if(cnt[e] == 1 || e == n) continue;
        auto v = yakusu(e);
        if(cnt[e] == 0) {
            invalid += calc(v.size());
            invalid %= mod;
            for(auto p : v) cnt[p]++;
        } else {
            invalid -= ((cnt[e] - 1) * calc(v.size())) % mod;
            invalid %= mod;
            ll gap = cnt[e] - 1;
            for(auto p : v) cnt[p]--;
            // for(auto p : v) cnt[p] -= gap;        <============================ これも通る
        }
    }
    ll sum = calc(vn.size());
    ll ans = sum - invalid + mod;
    ans %= mod;
    cout << ans << endl;
    return 0;
}
accuracy: 1
time_ms: 300
memory_kb: 19356
final_rank: 10

code_snippet: #include <bits/stdc++.h>
using namespace std;
typedef long long ll;
#define rep(i, srt, end) for (long long i = (srt); i < (long long)(end); i++)

vector<ll> yakusu(ll n){
    vector<ll> ret;
    for(ll i = 1; i*i <= n; i++){
        if(n % i != 0) continue;
        ret.push_back(i);
        if(i*i != n) ret.push_back(n/i);
    }
    sort(ret.begin(), ret.end());
    reverse(ret.begin(), ret.end());
    return ret;
}

const ll mod = 1000000000 + 7;
#define NMAX 1000010
ll fac[NMAX], inv[NMAX];

ll mod_pow(ll a, ll n, ll mod){
    ll ret = 1;
    while(n > 0){
        if(n & 1) ret = (ret*(a % mod))%mod;
        a = ((a%mod)*(a%mod)) % mod;
        n = n >> 1;
    }
    return ret;
}

ll mod_inv(ll a, ll mod){
    return mod_pow(a, mod-2, mod);
}

void mae_nck(){
    fac[1] = 1;
    inv[1] = 1;
    for(ll i = 2; i < NMAX; i++){
        fac[i] = (fac[i-1] * i)%mod;
        inv[i] = (inv[i-1] * mod_inv(i, mod))%mod;
    }
}

ll mod_nck(ll n, ll k){
    if (n < k) return 0;
    if (n < 0 || k < 0) return 0;
    if(k == 0 || k == n) return 1;
    ll ret = ((fac[n] * inv[k])%mod * inv[n-k])%mod;
    return ret;
}

ll calc(ll n) {
    ll res = 0;
    for(ll i = 1; i <= n; i++) {
        res += (mod_nck(n, i) * fac[i]) % mod;
        res %= mod; 
    }
    return res;
}

int main() {
    mae_nck();
    ll n;
    cin >> n;
    ll invalid = 0;
    auto vn = yakusu(n);
    map<ll, ll> cnt;
    for(auto e : vn) {
        if(cnt[e] == 1 || e == n) continue;
        auto v = yakusu(e);
        if(cnt[e] == 0) {
            invalid += calc(v.size());
            invalid %= mod;
            for(auto p : v) cnt[p]++;
        } else {
            invalid -= ((cnt[e] - 1) * calc(v.size())) % mod;
            int num = cnt[e] - 1;
            invalid %= mod;
            for(auto p : v) cnt[p] -= num;
        }
    }
    ll sum = calc(vn.size());
    ll ans = sum - invalid + mod;
    ans %= mod;
    cout << ans << endl;
    return 0;
}
accuracy: 1
time_ms: 290
memory_kb: 19452
final_rank: 9

code_snippet: #include <bits/stdc++.h>
using namespace std;
typedef long long ll;
#define rep(i, srt, end) for (long long i = (srt); i < (long long)(end); i++)

vector<ll> yakusu(ll n){
    vector<ll> ret;
    for(ll i = 1; i*i <= n; i++){
        if(n % i != 0) continue;
        ret.push_back(i);
        if(i*i != n) ret.push_back(n/i);
    }
    sort(ret.begin(), ret.end());
    reverse(ret.begin(), ret.end());
    return ret;
}

const ll mod = 1000000000 + 7;
#define NMAX 1000010
ll fac[NMAX], inv[NMAX];

ll mod_pow(ll a, ll n, ll mod){
    ll ret = 1;
    while(n > 0){
        if(n & 1) ret = (ret*(a % mod))%mod;
        a = ((a%mod)*(a%mod)) % mod;
        n = n >> 1;
    }
    return ret;
}

ll mod_inv(ll a, ll mod){
    return mod_pow(a, mod-2, mod);
}

void mae_nck(){
    fac[1] = 1;
    inv[1] = 1;
    for(ll i = 2; i < NMAX; i++){
        fac[i] = (fac[i-1] * i)%mod;
        inv[i] = (inv[i-1] * mod_inv(i, mod))%mod;
    }
}

ll mod_nck(ll n, ll k){
    if (n < k) return 0;
    if (n < 0 || k < 0) return 0;
    if(k == 0 || k == n) return 1;
    ll ret = ((fac[n] * inv[k])%mod * inv[n-k])%mod;
    return ret;
}

ll calc(ll n) {
    ll res = 0;
    for(ll i = 1; i <= n; i++) {
        res += (mod_nck(n, i) * fac[i]) % mod;
        res %= mod; 
    }
    return res;
}

int main() {
    mae_nck();
    ll n;
    cin >> n;
    ll invalid = 0;
    auto vn = yakusu(n);
    map<ll, ll> cnt;
    for(auto e : vn) {
        if(cnt[e] == 1 || e == n) continue;
        auto v = yakusu(e);
        if(cnt[e] == 0) {
            invalid += calc(v.size());
            invalid %= mod;
            for(auto p : v) cnt[p]++;
        } else {
            invalid -= ((cnt[e] - 1) * calc(v.size())) % mod;
            invalid %= mod;
            for(auto p : v) cnt[p] -= cnt[e] - 1;
        }
    }
    ll sum = calc(vn.size());
    ll ans = sum - invalid + mod;
    ans %= mod;
    cout << ans << endl;
    return 0;
}
accuracy: 0.06060606060606061
time_ms: 160
memory_kb: 19060
final_rank: 19

code_snippet: #include <bits/stdc++.h>
using namespace std;
typedef long long ll;
#define rep(i, srt, end) for (long long i = (srt); i < (long long)(end); i++)

vector<ll> yakusu(ll n){
    vector<ll> ret;
    for(ll i = 1; i*i <= n; i++){
        if(n % i != 0) continue;
        ret.push_back(i);
        if(i*i != n) ret.push_back(n/i);
    }
    sort(ret.begin(), ret.end());
    reverse(ret.begin(), ret.end());
    return ret;
}

const ll mod = 1000000000 + 7;
#define NMAX 1000010
ll fac[NMAX], inv[NMAX];

ll mod_pow(ll a, ll n, ll mod){
    ll ret = 1;
    while(n > 0){
        if(n & 1) ret = (ret*(a % mod))%mod;
        a = ((a%mod)*(a%mod)) % mod;
        n = n >> 1;
    }
    return ret;
}

ll mod_inv(ll a, ll mod){
    return mod_pow(a, mod-2, mod);
}

void mae_nck(){
    fac[1] = 1;
    inv[1] = 1;
    for(ll i = 2; i < NMAX; i++){
        fac[i] = (fac[i-1] * i)%mod;
        inv[i] = (inv[i-1] * mod_inv(i, mod))%mod;
    }
}

ll mod_nck(ll n, ll k){
    if (n < k) return 0;
    if (n < 0 || k < 0) return 0;
    if(k == 0 || k == n) return 1;
    ll ret = ((fac[n] * inv[k])%mod * inv[n-k])%mod;
    return ret;
}

ll calc(ll n) {
    ll res = 0;
    for(ll i = 1; i <= n; i++) {
        res += (mod_nck(n, i) * fac[i]) % mod;
        res %= mod; 
    }
    return res;
}

int main() {
    mae_nck();
    ll n;
    cin >> n;
    ll invalid = 0;
    auto vn = yakusu(n);
    map<ll, ll> cnt;
    for(auto e : vn) {
        if(cnt[e] == 1 || e == n) continue;
        auto v = yakusu(e);
        if(cnt[e] == 0) {
            invalid += calc(v.size());
            invalid %= mod;
            for(auto p : v) cnt[p]++;
        } else {
            invalid -= ((cnt[e] - 1) * calc(v.size())) % mod;
            invalid %= mod;
            for(auto p : v) cnt[p]--;
        }
    }
    ll sum = calc(vn.size());
    ll ans = sum - invalid + mod;
    ans %= mod;
    cout << ans << endl;
    return 0;
}
accuracy: 1
time_ms: 300
memory_kb: 19396
final_rank: 11

code_snippet: #include <bits/stdc++.h>
using namespace std;

template <int mod = (int)(1e9 + 7)>
struct ModInt {
  int x;
  constexpr ModInt() : x(0) {}
  constexpr ModInt(int64_t y)
      : x(y >= 0 ? y % mod : (mod - (-y) % mod) % mod) {}
  constexpr ModInt &operator+=(const ModInt &p) noexcept {
    if ((x += p.x) >= mod) x -= mod;
    return *this;
  }
  constexpr ModInt &operator-=(const ModInt &p) noexcept {
    if ((x += mod - p.x) >= mod) x -= mod;
    return *this;
  }
  constexpr ModInt &operator*=(const ModInt &p) noexcept {
    x = (int)(1LL * x * p.x % mod);
    return *this;
  }
  constexpr ModInt &operator/=(const ModInt &p) noexcept {
    *this *= p.inverse();
    return *this;
  }
  constexpr ModInt operator-() const { return ModInt(-x); }
  constexpr ModInt operator+(const ModInt &p) const noexcept {
    return ModInt(*this) += p;
  }
  constexpr ModInt operator-(const ModInt &p) const noexcept {
    return ModInt(*this) -= p;
  }
  constexpr ModInt operator*(const ModInt &p) const noexcept {
    return ModInt(*this) *= p;
  }
  constexpr ModInt operator/(const ModInt &p) const noexcept {
    return ModInt(*this) /= p;
  }
  constexpr bool operator==(const ModInt &p) const noexcept { return x == p.x; }
  constexpr bool operator!=(const ModInt &p) const noexcept { return x != p.x; }
  constexpr ModInt inverse() const noexcept {
    int a = x, b = mod, u = 1, v = 0, t = 0;
    while (b > 0) {
      t = a / b;
      swap(a -= t * b, b);
      swap(u -= t * v, v);
    }
    return ModInt(u);
  }
  constexpr ModInt pow(int64_t n) const {
    ModInt res(1), mul(x);
    while (n) {
      if (n & 1) res *= mul;
      mul *= mul;
      n >>= 1;
    }
    return res;
  }
  friend constexpr ostream &operator<<(ostream &os, const ModInt &p) noexcept {
    return os << p.x;
  }
  friend constexpr istream &operator>>(istream &is, ModInt &a) noexcept {
    int64_t t = 0;
    is >> t;
    a = ModInt<mod>(t);
    return (is);
  }
  constexpr int get_mod() { return mod; }
};

struct Combination {
  vector<ModInt<>> _fact, _rfact, _inv;
  Combination(long long nsize = 5000000)
      : _fact(nsize + 1), _rfact(nsize + 1), _inv(nsize + 1) {
    _fact[0] = _rfact[nsize] = _inv[0] = 1;
    for (int i = 1; i <= nsize; i++) _fact[i] = _fact[i - 1] * i;
    _rfact[nsize] /= _fact[nsize];
    for (int i = nsize - 1; i >= 0; i--) _rfact[i] = _rfact[i + 1] * (i + 1);
    for (int i = 1; i <= nsize; i++) _inv[i] = _rfact[i] * _fact[i - 1];
  }
  inline ModInt<> fact(int k) const { return _fact[k]; }

  inline ModInt<> rfact(int k) const { return _rfact[k]; }

  inline ModInt<> inv(int k) const { return _inv[k]; }

  ModInt<> P(int n, int r) const {
    if (r < 0 || n < r) return 0;
    return fact(n) * rfact(n - r);
  }

  ModInt<> C(int p, int q) const {
    if (q < 0 || p < q) return 0;
    return fact(p) * rfact(q) * rfact(p - q);
  }
  // n types,choose r
  ModInt<> H(int n, int r) const {
    if (n < 0 || r < 0) return (0);
    return r == 0 ? 1 : C(n + r - 1, r);
  }
};

map<long long, long long> div_moebius(long long n, vector<long long> &primes) {
  map<long long, long long> res;
  for (long long i = 2; i * i <= n; ++i)
    if (n % i == 0) {
      primes.push_back(i);
      while (n % i == 0) n /= i;
    }
  if (n > 1) primes.push_back(n);
  n = primes.size();
  for (long long i = 0; i < (1 << n); ++i) {
    long long mu = 1, d = 1;
    for (long long j = 0; j < n; ++j)
      if (i >> j & 1) {
        mu *= -1;
        d *= primes[j];
      }
    res[d] = mu;
  }
  return res;
}

long long n;
Combination com;
vector<ModInt<>> rsum;

ModInt<> solve();

int main() {
  {
    int len = com._rfact.size();
    rsum.assign(len, 1);
    for (int i = 1; i < len; ++i) rsum[i] = rsum[i - 1] + com.rfact(i);
  }
  cin >> n;
  cout << solve() << endl;
  return 0;
}

ModInt<> solve() {
  ModInt<> res = 0;
  vector<long long> primes, divisors;
  map<long long, long long> mb = div_moebius(n, primes), cnt;
  for (long long i = 1; i * i <= n; ++i)
    if (n % i == 0) {
      divisors.push_back(i);
      if (i * i != n) divisors.push_back(n / i);
    }
  sort(divisors.begin(), divisors.end());
  cnt[1] = 1;
  for (auto d : divisors)
    for (auto p : primes)
      if (d % p == 0) {
        long long now = 1, tmp = d;
        while (tmp % p == 0) ++now, tmp /= p;
        cnt[d] = cnt[d / p] * now / (now - 1);
        break;
      }
  for (auto p : mb) {
    long long d = n / p.first, u = p.second, c = 0;
    c = cnt[d];
    res += com.fact(c) * rsum[c - 1] * u;
  }
  return res;
}
accuracy: 1
time_ms: 60
memory_kb: 81692
final_rank: 6

code_snippet: #include <iostream>
#include <string>
#include <vector>
#include <array>
#include <queue>
#include <deque>
#include <algorithm>
#include <set>
#include <map>
#include <bitset>
#include <cmath>
#include <functional>
#include <cassert>
#include <iomanip>
#define vll vector<ll>
#define vvvl vector<vvl>
#define vvl vector<vector<ll>>
#define VV(a, b, c, d) vector<vector<d>>(a, vector<d>(b, c))
#define VVV(a, b, c, d) vector<vvl>(a, vvl(b, vll (c, d)));
#define re(c, b) for(ll c=0;c<b;c++)
#define all(obj) (obj).begin(), (obj).end()
typedef long long int ll;
typedef long double ld;
using namespace std;

namespace fact{
  ll gcd(ll _a, ll _b) {
    unsigned long long a = abs(_a), b = abs(_b);
    if(a == 0) return b;
    if(b == 0) return a;
    int shift = __builtin_ctzll(a | b);
    a >>= __builtin_ctzll(a);
    do {
      b >>= __builtin_ctzll(b);
      if(a > b) std::swap(a, b);
      b -= a;
    }while(b);
    return (a << shift);
  }
  template <class T, class U>
  T modpow(T x, U n, T md) {
      T r = 1 % md;
      x %= md;
      while(n) {
          if(n & 1) r = (r * x) % md;
          x = (x * x) % md;
          n >>= 1;
      }
      return r;
  }
  bool is_prime(ll n) {
    if(n<=1) return false;
    if(n==2) return true;
    if(n%2==0) return false;
    ll d = n - 1;
    while(d % 2 == 0) d /= 2;
    for(ll a : {2, 3, 5, 7, 11, 13, 17, 19, 23, 29, 31, 37}) {
      if(n <= a) break;
      ll t = d, y = modpow<__int128_t>(a, t, n);
      while(t != n - 1 && y != 1 && y != n - 1) {
        y = __int128_t(y) * y % n, t <<= 1;
      }
      if(y != n - 1 && t % 2 == 0) {
        return false;
      }
    }
    return true;
  }
  ll rho(ll n){
    if(is_prime(n)) return n;
    if(n % 2 == 0) return 2;
    ll c = 0;
    while(true){
      c = (3 * c + 1) % 24;
      auto f = [&](ll x){return(__int128_t(x)*x+c)%n;};
      ll st = 0;
      while(true){
        st++;
        ll x = st%n, y = f(x);
        while(true){
          ll g = gcd(abs(x-y), n);
          if(g==1) x = f(x), y = f(f(y));
          else if(g==n) break;
          else return g;
        }
      }
    }
  }
  vll factorize(ll n) {
    if(n == 1) return {};
    ll x = rho(n);
    if(x == n) return {x};
    vll le = factorize(x);
    vll ri = factorize(n / x);
    le.insert(le.end(), ri.begin(), ri.end());
    return le;
  }
}

#define P 1000000007
#define N_MAX 5000000
ll fac[N_MAX+1], inv[N_MAX+1], finv[N_MAX+1];
ll comb(ll n, ll k){
  if(n<0||k<0||n<k) return 0;
  return (((fac[n]*finv[n-k])%P)*finv[k])%P;
}
ll perm(ll n, ll k){
  if(n<0||k<0||n<k) return 0;
  return (fac[n]*finv[n-k])%P;
}
void init(){
  fac[0] = finv[0] = fac[1] = finv[1] = inv[1] = 1;
  for(int i = 2; i <= N_MAX; i++){
    fac[i] = (fac[i-1]*i)%P;
    inv[i] = ((-(P/i)*inv[P%i])%P+P)%P;
    finv[i] = (finv[i-1]*inv[i])%P;
  }
}
ll pp(ll a, ll b){ return (a * b)%P;}
ll mpow(ll a, ll b, ll p = -1){
  ll ret = 1, num = a;
  while(b>0){
    if(b&1) ret = (ret*num)%p;
    num = (num*num)%p;
    b /= 2;
  }
  return ret;
}
vll fiacc(N_MAX, 1);

ll nn;
ll trans(ll n){
  if(n < 1200000) return n;
  //if(n>=1500000) std::cout << "err" << n << '\n';
  return nn/n + 1500000;
}

int main(){
  ll n;std::cin >> n;
  nn = n;
  init();
  for(int i=1;i<N_MAX;i++) fiacc[i] = (fiacc[i-1] + finv[i])%P;
  vll d;
  for(ll i=1;i*i<=n;i++){
    if(n%i) continue;
    d.push_back(i);
    if(i*i!=n) d.push_back(n/i);
  }
  ll N = d.size();
  vll ans(3000000, 0);
  ans[1] = 1;
  if(n==1){
    std::cout << 1 << '\n';
    return 0;
  }

  sort(all(d));
  for(int i=1;i<N;i++){
    ll cnt = 0;
    ll num = d[i];
    ll now = trans(num);

    for(ll j=1;j*j<=num;j++){
      if(num%j!=0) continue;
      cnt++;
      ans[now] = (ans[now] - ans[trans(j)] + P)%P;
      if(j*j!=num){
        cnt++;
        ll to = trans(num/j);
        if(j!=1) ans[now] = (ans[now] - ans[to] + P)%P;
      }
    }
    ans[now] = (ans[now] + pp(fac[cnt], fiacc[cnt-1]))%P;
    if(i==N-1) std::cout << ans[now] << '\n';
  }
}
accuracy: 1
time_ms: 400
memory_kb: 182956
final_rank: 13

code_snippet: #include <bits/stdc++.h>
using namespace std;
using Int = long long;
int PREP = (cin.tie(nullptr), ios::sync_with_stdio(false), cout << fixed << setprecision(12), 0);
//int SEGV = getenv("D") || (exit(system("D= SEGFAULT_SIGNALS=all catchsegv ./prog.exe") >> 8), 0);
const Int MOD = 998244353;
Int POW2[4100000];
int main() {
    POW2[0] = 1;
    for (int i = 1; i < 4100000; i++) {
        POW2[i] = POW2[i - 1] * 2 % MOD;
    }
    int N, M, K, F; cin >> N >> M >> K >> F;
    vector<int> A(M), B(M), C(M);
    for (int i = 0; i < M; i++) {
        cin >> A[i] >> B[i] >> C[i];
        A[i]--, B[i]--;
    }
    Int ans = 1;
    for (int i = 0; i < K; i++) {
        int k = (N - 1) * (N - 2);
        for (int j = 0; j < M; j++) {
            if (abs(A[j] - B[j]) >= 2) {
                k--;
            } else {
                if (C[j] & (1 << i)) {
                    k = -1;
                }
            }
        }
        Int total = POW2[N * N - M];
        Int zero = (k < 0 ? 0 : POW2[k]);
        Int one = (total - zero + MOD) % MOD;
        if (F & (1 << i)) {
            ans *= one;
        } else {
            ans *= zero;
        }
        ans %= MOD;
    }
    cout << ans << '\n';
    return 0;
}
accuracy: 0.030303030303030304
time_ms: 10
memory_kb: 35468
final_rank: 20

code_snippet: #include <bits/stdc++.h>
 
const double pi = 3.141592653589793238462643383279;
using namespace std;

//typedef
//------------------------------------------
typedef vector<int> VI;
typedef vector<VI> VVI;
typedef vector<string> VS;
typedef pair<int, int> PII;
typedef pair<long long, long long> PLL;
typedef pair<int, PII> TIII;
typedef long long LL;
typedef unsigned long long ULL;
typedef vector<LL> VLL;
typedef vector<VLL> VVLL;
 
 
//container util
//------------------------------------------
#define ALL(a)  (a).begin(),(a).end()
#define RALL(a) (a).rbegin(), (a).rend()
#define PB push_back
#define MP make_pair
#define SQ(a) ((a)*(a))
#define EACH(i,c) for(typeof((c).begin()) i=(c).begin(); i!=(c).end(); ++i)
#define EXIST(s,e) ((s).find(e)!=(s).end())
#define SORT(c) sort((c).begin(),(c).end())
 
 
//repetition
//------------------------------------------
#define FOR(i,s,n) for(int i=s;i<(int)n;++i)
#define REP(i,n) FOR(i,0,n)
#define MOD 1000000007
 
 
#define rep(i, a, b) for(int i = a; i < (b); ++i)
#define trav(a, x) for(auto& a : x)
#define all(x) x.begin(), x.end()
#define sz(x) (int)(x).size()
 
typedef long long ll;
typedef pair<int, int> pii;
typedef vector<int> vi;
 
#define chmin(x,y) x=min(x,y)
#define chmax(x,y) x=max(x,y)

const long double EPS = 1e-6, PI = acos((long double)-1);

//ここから編集

 
const int MAX = 2000010;
long long fac[MAX], finv[MAX], inv[MAX];
 
// テーブルを作る前処理
void COMinit() {
    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 % MOD;
        inv[i] = MOD - inv[MOD%i] * (MOD / i) % MOD;
        finv[i] = finv[i - 1] * inv[i] % MOD;
    }
}
 
// 二項係数計算
long long COM(int n, int k){
    if (n < k) return 0;
    if (n < 0 || k < 0) return 0;
    return fac[n] * (finv[k] * finv[n - k] % MOD) % MOD;
}
ll GCD(ll a, ll b){
  if(b == 0) return a;
  return GCD(b, a%b);
}
ll LCM(ll a, ll b){
  return a/GCD(a, b)*b;
}

unordered_map<ll, vector<ll>> mp;
int main() {
  cin.tie(0);
  ios::sync_with_stdio(false);
  cout << fixed << setprecision(10);
 
  ll N; cin >> N;

  vector<ll> divisor;
  for(ll i=1; i*i<=N; i++){
    if(N%i == 0){
      if(N/i != i){
        divisor.push_back(i);
        divisor.push_back(N/i);
      }else{
        divisor.push_back(i);
      }
    }
  }
  sort(all(divisor));
  
  mp[0].resize(1010);
  mp[0][0] = 1;
  
  for(int i=0; i<divisor.size(); i++){

    for(int sz=(int)divisor.size()-1; sz>=0; sz--){
      for(auto e: mp){
        
        ll a = e.first;
        ll t = a;
        if(a == 0) t = 1;
        ll lcm = LCM(t, divisor[i]);

        if(mp.find(lcm) == mp.end()){
          mp[lcm].resize(1010);
          mp[lcm][sz+1] += mp[a][sz];
          mp[lcm][sz+1] %= MOD;
        }else{
          mp[lcm][sz+1] += mp[a][sz];
          mp[lcm][sz+1] %= MOD;
        }
      }
    }
  }

  COMinit();
  ll ans = 0;
  for(int i=0; i<=divisor.size(); i++){
    
    if(mp[N][i] != 0){
      ans += fac[i] * mp[N][i] % MOD;
      ans %= MOD;
    }
  }
  cout << ans << endl;
  return 0;
}
accuracy: 0.696969696969697
time_ms: 220
memory_kb: 50480
final_rank: 17

code_snippet: #include <bits/stdc++.h>
 
const double pi = 3.141592653589793238462643383279;
using namespace std;

//typedef
//------------------------------------------
typedef vector<int> VI;
typedef vector<VI> VVI;
typedef vector<string> VS;
typedef pair<int, int> PII;
typedef pair<long long, long long> PLL;
typedef pair<int, PII> TIII;
typedef long long LL;
typedef unsigned long long ULL;
typedef vector<LL> VLL;
typedef vector<VLL> VVLL;
 
 
//container util
//------------------------------------------
#define ALL(a)  (a).begin(),(a).end()
#define RALL(a) (a).rbegin(), (a).rend()
#define PB push_back
#define MP make_pair
#define SQ(a) ((a)*(a))
#define EACH(i,c) for(typeof((c).begin()) i=(c).begin(); i!=(c).end(); ++i)
#define EXIST(s,e) ((s).find(e)!=(s).end())
#define SORT(c) sort((c).begin(),(c).end())
 
 
//repetition
//------------------------------------------
#define FOR(i,s,n) for(int i=s;i<(int)n;++i)
#define REP(i,n) FOR(i,0,n)
#define MOD 1000000007
 
 
#define rep(i, a, b) for(int i = a; i < (b); ++i)
#define trav(a, x) for(auto& a : x)
#define all(x) x.begin(), x.end()
#define sz(x) (int)(x).size()
 
typedef long long ll;
typedef pair<int, int> pii;
typedef vector<int> vi;
 
#define chmin(x,y) x=min(x,y)
#define chmax(x,y) x=max(x,y)

const long double EPS = 1e-6, PI = acos((long double)-1);

//ここから編集

 
const int MAX = 2000010;
long long fac[MAX], finv[MAX], inv[MAX];
 
// テーブルを作る前処理
void COMinit() {
    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 % MOD;
        inv[i] = MOD - inv[MOD%i] * (MOD / i) % MOD;
        finv[i] = finv[i - 1] * inv[i] % MOD;
    }
}
 
// 二項係数計算
long long COM(int n, int k){
    if (n < k) return 0;
    if (n < 0 || k < 0) return 0;
    return fac[n] * (finv[k] * finv[n - k] % MOD) % MOD;
}
ll GCD(ll a, ll b){
  return (b==0)?a:GCD(b, a%b);
}
ll LCM(ll a, ll b){
  return a/GCD(a, b)*b;
}

unordered_map<ll, vector<ll>> mp;
int main() {
  cin.tie(0);
  ios::sync_with_stdio(false);
  cout << fixed << setprecision(10);
 
  ll N; cin >> N;

  vector<ll> divisor;
  for(ll i=1; i*i<=N; i++){
    if(N%i == 0){
      if(N/i != i){
        divisor.push_back(i);
        divisor.push_back(N/i);
      }else{
        divisor.push_back(i);
      }
    }
  }
  sort(all(divisor));
  
  mp[0].resize(510);
  mp[0][0] = 1;
  
  for(int i=0; i<divisor.size(); i++){

    for(int sz=(int)divisor.size()-1; sz>=0; sz--){
      for(auto e: mp){
        
        ll a = e.first;
        ll t = a;
        if(a == 0) t = 1;
        ll lcm = LCM(t, divisor[i]);

        if(mp.find(lcm) == mp.end()){
          mp[lcm].resize(510);
          mp[lcm][sz+1] += mp[a][sz];
          mp[lcm][sz+1] %= MOD;
        }else{
          mp[lcm][sz+1] += mp[a][sz];
          mp[lcm][sz+1] %= MOD;
        }
      }
    }
  }

  COMinit();
  ll ans = 0;
  for(int i=0; i<510; i++){
    
    if(mp[N].size() != 0 &&  mp[N][i] != 0){
      ans += fac[i] * mp[N][i] % MOD;
      ans %= MOD;
    }
  }
  cout << ans << endl;
  return 0;
}
accuracy: 0.696969696969697
time_ms: 170
memory_kb: 50300
final_rank: 16

code_snippet: #include <bits/stdc++.h>
 
const double pi = 3.141592653589793238462643383279;
using namespace std;

//typedef
//------------------------------------------
typedef vector<int> VI;
typedef vector<VI> VVI;
typedef vector<string> VS;
typedef pair<int, int> PII;
typedef pair<long long, long long> PLL;
typedef pair<int, PII> TIII;
typedef long long LL;
typedef unsigned long long ULL;
typedef vector<LL> VLL;
typedef vector<VLL> VVLL;
 
 
//container util
//------------------------------------------
#define ALL(a)  (a).begin(),(a).end()
#define RALL(a) (a).rbegin(), (a).rend()
#define PB push_back
#define MP make_pair
#define SQ(a) ((a)*(a))
#define EACH(i,c) for(typeof((c).begin()) i=(c).begin(); i!=(c).end(); ++i)
#define EXIST(s,e) ((s).find(e)!=(s).end())
#define SORT(c) sort((c).begin(),(c).end())
 
 
//repetition
//------------------------------------------
#define FOR(i,s,n) for(int i=s;i<(int)n;++i)
#define REP(i,n) FOR(i,0,n)
#define MOD 1000000007
 
 
#define rep(i, a, b) for(int i = a; i < (b); ++i)
#define trav(a, x) for(auto& a : x)
#define all(x) x.begin(), x.end()
#define sz(x) (int)(x).size()
 
typedef long long ll;
typedef pair<int, int> pii;
typedef vector<int> vi;
 
#define chmin(x,y) x=min(x,y)
#define chmax(x,y) x=max(x,y)

const long double EPS = 1e-6, PI = acos((long double)-1);

//ここから編集

 
const int MAX = 2000010;
long long fac[MAX], finv[MAX], inv[MAX];
 
// テーブルを作る前処理
void COMinit() {
    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 % MOD;
        inv[i] = MOD - inv[MOD%i] * (MOD / i) % MOD;
        finv[i] = finv[i - 1] * inv[i] % MOD;
    }
}
 
// 二項係数計算
long long COM(int n, int k){
    if (n < k) return 0;
    if (n < 0 || k < 0) return 0;
    return fac[n] * (finv[k] * finv[n - k] % MOD) % MOD;
}
ll GCD(ll a, ll b){
  return (b==0)?a:GCD(b, a%b);
}
ll LCM(ll a, ll b){
  return a/GCD(a, b)*b;
}

unordered_map<ll, vector<ll>> mp;
int main() {
  cin.tie(0);
  ios::sync_with_stdio(false);
  cout << fixed << setprecision(10);
 
  ll N; cin >> N;

  vector<ll> divisor;
  for(ll i=1; i*i<=N; i++){
    if(N%i == 0){
      if(N/i != i){
        divisor.push_back(i);
        divisor.push_back(N/i);
      }else{
        divisor.push_back(i);
      }
    }
  }
  sort(all(divisor));
  
  mp[0].resize(310);
  mp[0][0] = 1;
  
  for(int i=0; i<divisor.size(); i++){

    for(int sz=(int)divisor.size()-1; sz>=0; sz--){
      for(auto e: mp){
        
        ll a = e.first;
        ll t = a;
        if(a == 0) t = 1;
        ll lcm = LCM(t, divisor[i]);

        if(mp.find(lcm) == mp.end()){
          mp[lcm].resize(310);
          mp[lcm][sz+1] += mp[a][sz];
          mp[lcm][sz+1] %= MOD;
        }else{
          mp[lcm][sz+1] += mp[a][sz];
          mp[lcm][sz+1] %= MOD;
        }
      }
    }
  }

  COMinit();
  ll ans = 0;
  for(int i=0; i<310; i++){
    
    if(mp[N].size() != 0 &&  mp[N][i] != 0){
      ans += fac[i] * mp[N][i] % MOD;
      ans %= MOD;
    }
  }
  cout << ans << endl;
  return 0;
}
accuracy: 0.696969696969697
time_ms: 130
memory_kb: 50364
final_rank: 15