結果
問題 | No.430 文字列検索 |
ユーザー | AC2K |
提出日時 | 2023-03-29 13:24:43 |
言語 | C++23 (gcc 12.3.0 + boost 1.83.0) |
結果 |
AC
|
実行時間 | 264 ms / 2,000 ms |
コード長 | 3,921 bytes |
コンパイル時間 | 2,676 ms |
コンパイル使用メモリ | 262,004 KB |
実行使用メモリ | 27,264 KB |
最終ジャッジ日時 | 2024-11-10 01:05:51 |
合計ジャッジ時間 | 4,173 ms |
ジャッジサーバーID (参考情報) |
judge5 / judge2 |
(要ログイン)
テストケース
テストケース表示入力 | 結果 | 実行時間 実行使用メモリ |
---|---|---|
testcase_00 | AC | 1 ms
5,248 KB |
testcase_01 | AC | 264 ms
27,264 KB |
testcase_02 | AC | 11 ms
5,248 KB |
testcase_03 | AC | 12 ms
5,248 KB |
testcase_04 | AC | 2 ms
5,248 KB |
testcase_05 | AC | 2 ms
5,248 KB |
testcase_06 | AC | 1 ms
5,248 KB |
testcase_07 | AC | 2 ms
5,248 KB |
testcase_08 | AC | 241 ms
27,008 KB |
testcase_09 | AC | 2 ms
5,248 KB |
testcase_10 | AC | 15 ms
5,888 KB |
testcase_11 | AC | 79 ms
8,192 KB |
testcase_12 | AC | 80 ms
8,192 KB |
testcase_13 | AC | 77 ms
8,192 KB |
testcase_14 | AC | 67 ms
6,528 KB |
testcase_15 | AC | 49 ms
5,760 KB |
testcase_16 | AC | 16 ms
5,248 KB |
testcase_17 | AC | 13 ms
5,248 KB |
ソースコード
#line 2 "template.hpp" #include<bits/stdc++.h> using namespace std; #define rep(i, N) for(int i=0;i<(N);i++) #define all(x) (x).begin(),(x).end() #define popcount(x) __builtin_popcount(x) using i128=__int128_t; using ll = long long; using ld = long double; using graph = vector<vector<int>>; using P = pair<int, int>; constexpr int inf = 1e9; constexpr ll infl = 1e18; constexpr ld eps = 1e-6; const long double pi = acos(-1); constexpr uint64_t MOD = 1e9 + 7; constexpr uint64_t MOD2 = 998244353; constexpr int dx[] = { 1,0,-1,0 }; constexpr int dy[] = { 0,1,0,-1 }; template<class T>static constexpr inline void chmax(T&x,T y){if(x<y)x=y;} template<class T>static constexpr inline void chmin(T&x,T y){if(x>y)x=y;} #line 2 "math/mod_pow.hpp" template <class T, class U = T> U mod_pow(T base, T exp, T mod){ T ans = 1; base %= mod; while (exp > 0) { if (exp & 1) { ans *= base; ans %= mod; } base *= base; base %= mod; exp >>= 1; } return ans; } ///@brief mod pow(バイナリ法) #line 3 "string/rolling_hash.hpp" class RollingHash { using ull = uint_fast64_t; using i128 = __int128_t; using u128 = __uint128_t; // mod static constexpr ull msk30 = (1ul << 30) - 1; static constexpr ull msk61 = (1ul << 31) - 1; string str; vector<ull> hash, pow; static constexpr ull mod = (1uL << 61) - 1; static constexpr ull primitive_root = 37; public: static const uint mapping_max = (uint)'Z' + 2; static ull base; private: ull mul(const u128& a,const u128& b) const { u128 t = a * b; t = (t >> 61) + (t & mod); if (t >= mod) { t -= mod; } return t; } ull mapping(const char& c) const { return (ull)c; //変更する? } static ull generate() { mt19937_64 engine(chrono::steady_clock::now().time_since_epoch().count()); uniform_int_distribution<ull> rand(1uL, mod - 1); return rand(engine); } static void generate_base() { if (base != 0){ return; } ull r = mod - 1; while (gcd(r, mod - 1) != 1 || r <= mapping_max){ r = generate(); } base = mod_pow<__uint128_t>(primitive_root, r, mod); } public: RollingHash() :str() { } RollingHash(const string& str) :str(str) { generate_base(); build(); } void build() { hash.resize(str.size() + 1); pow.resize(str.size() + 1, 1); for (int i = 0; i < str.size(); i++) { hash[i + 1] = mul(hash[i], base) + mapping(str[i]); pow[i + 1] = mul(pow[i], base); if (hash[i + 1] >= mod) { hash[i + 1] -= mod; } } } ull range(int l, int r) const { ull res = mod + hash[r] - mul(hash[l], pow[r - l]); return res < mod ? res : res - mod; } ull get_all() const { return hash.back(); } int size() const {return str.size();} static int lcp(const RollingHash &a, const RollingHash &b, const int &start_a, const int &start_b) { int ok = 0; int ng = min(a.size() - start_a, b.size() - start_b) + 1; while (abs(ok - ng) > 1){ int md = (ok + ng) >> 1; if (a.range(start_a, start_a + md) == b.range(start_b, start_b + md)){ ok = md; } else{ ng = md; } } return ok; } }; typename RollingHash::ull RollingHash::base; ///@brief Rollinghash(ローリングハッシュ) #line 3 "main.cpp" #pragma GCC target("avx2") #pragma GCC optimize("Ofast") #pragma GCC optimize("unroll-loops") int main(){ string s; int m; cin >> s >> m; RollingHash S(s); map<uint64_t, int> hash_count; rep(i, s.size()) { for (int length = 1; length <= 10 && i + length <= s.size(); length++) { int j = i + length; hash_count[S.range(i, j)]++; } } long long ans = 0; for (int i = 0; i < m; i++) { string c; cin >> c; ans += hash_count[RollingHash(c).get_all()]; } cout << ans << '\n'; }