이 제출은 이전 버전의 oj.uz에서 채점하였습니다. 현재는 제출 당시와는 다른 서버에서 채점을 하기 때문에, 다시 제출하면 결과가 달라질 수도 있습니다.
#include <bits/stdc++.h>
using namespace std;
const int Nmax = 1e6 + 5;
struct segment
{
int x, y;
};
struct query
{
segment s; int id;
};
map<char, int> code;
vector<query> queries[Nmax];
vector<int> v[Nmax];
int pref[Nmax], suff[Nmax], n, ans[Nmax];
char *s[Nmax], A[Nmax], B[Nmax], S[Nmax];
struct Trie
{
int n, tmp;
int nxt[Nmax][4], in[Nmax], out[Nmax];
void add(char *s, int node = 0)
{
if(!s[0]) return;
int go = code[s[0]];
if(!nxt[node][go]) nxt[node][go] = ++n;
add(s+1, nxt[node][go]);
}
int search_pos(char *s, int node = 0)
{
if(!s[0]) return node;
int go = code[s[0]];
if(!nxt[node][go]) return -1;
return search_pos(s+1, nxt[node][go]);
}
void dfs(int node = 0)
{
int i;
in[node] = ++tmp;
for(i=0; i<4; ++i)
if(nxt[node][i]) dfs(nxt[node][i]);
out[node] = tmp;
}
segment search_subarb(char *s)
{
int node = search_pos(s);
if(node == -1) return {-1, -1};
return {in[node], out[node]};
}
} one, two;
struct AIB
{
int a[Nmax];
int ub(int x) { return (x&(-x)); }
public:
void update(int pos)
{
for(; pos <= two.tmp; pos += ub(pos)) ++a[pos];
}
int query(segment K)
{
int x = K.x, y = K.y;
int ans = 0;
for(; y; y-=ub(y)) ans += a[y];
for(--x; x; x-=ub(x)) ans -= a[x];
return ans;
}
} aib;
void precalc()
{
int i;
for(i=1; i<=n; ++i) one.add(s[i]);
one.dfs();
for(i=1; i<=n; ++i)
pref[i] = one.search_pos(s[i]);
for(i=1; i<=n; ++i)
{
int L = strlen(s[i]);
reverse(s[i], s[i] + L);
two.add(s[i]);
}
two.dfs();
for(i=1; i<=n; ++i)
suff[i] = two.search_pos(s[i]);
for(i=1; i<=n; ++i)
v[one.in[pref[i]]].push_back(two.in[suff[i]]);
}
int main()
{
// freopen("input", "r", stdin);
cin.sync_with_stdio(false);
code['A'] = 0; code['G'] = 1; code['C'] = 2; code['U'] = 3;
int i, q;
scanf("%d %d\n", &n, &q);
for(i=1; i<=n; ++i)
{
scanf("%s\n", S);
int L = strlen(S);
s[i] = new char [L + 1];
memcpy(s[i], S, L);
}
precalc();
for(i=1; i<=q; ++i)
{
scanf("%s %s\n", A, B);
int L = strlen(B);
reverse(B, B+L);
segment before, after;
before = one.search_subarb(A);
after = two.search_subarb(B);
if(before.x == -1 || after.x == -1) continue;
queries[before.x - 1].push_back({after, -i});
queries[before.y].push_back({after, i});
}
for(i=1; i<=one.tmp; ++i)
{
for(auto it : v[i]) aib.update(it);
for(auto it : queries[i])
{
int res = aib.query(it.s);
if(it.id > 0) ans[it.id] += res;
else ans[-it.id] -= res;
}
}
for(i=1; i<=q; ++i) printf("%d\n", ans[i]);
return 0;
}
컴파일 시 표준 에러 (stderr) 메시지
selling_rna.cpp: In function 'int main()':
selling_rna.cpp:116:10: warning: ignoring return value of 'int scanf(const char*, ...)', declared with attribute warn_unused_result [-Wunused-result]
scanf("%d %d\n", &n, &q);
~~~~~^~~~~~~~~~~~~~~~~~~
selling_rna.cpp:119:14: warning: ignoring return value of 'int scanf(const char*, ...)', declared with attribute warn_unused_result [-Wunused-result]
scanf("%s\n", S);
~~~~~^~~~~~~~~~~
selling_rna.cpp:129:14: warning: ignoring return value of 'int scanf(const char*, ...)', declared with attribute warn_unused_result [-Wunused-result]
scanf("%s %s\n", A, B);
~~~~~^~~~~~~~~~~~~~~~~
# | Verdict | Execution time | Memory | Grader output |
---|
Fetching results... |
# | Verdict | Execution time | Memory | Grader output |
---|
Fetching results... |
# | Verdict | Execution time | Memory | Grader output |
---|
Fetching results... |
# | Verdict | Execution time | Memory | Grader output |
---|
Fetching results... |