最小距离查询
时间限制 1000 ms 内存限制 65536 KB
题目描述
给定一个由小写字母a到z组成的字符串S,其中第i个字符为S[i](下标从0开始)。你需要完成下面两个操作:
INSERT c
其中c是一个待输入的字符。你需要在字符串的末尾添加这个字符。保证输入的字符同样是a到z之间的一个小写字母。
QUERY x
其中x是一个输入的整数下标。对于这个询问,你需要回答在S当中和S[x]相等且与x最近的距离。输入保证x在当前字符串中合法。
例如S = "abcaba",如果我们操作:
INSERT a
则在S的末端加一个字符a,S变成"abcabaa"。
接下来操作
QUERY 0
由于S[0] = a,在S中出现的离他最近的a在下标为3的位置上,距离为3 - 0 = 3。因此应当输出3。
接下来,如果
QUERY 4
S[4] = b,S中离它最近的b出现在下标为1处,距离为4 - 1 = 3。同样应当输出3。
给定初始字符串S和若干操作,对于每个QUERY,你需要求出相应的距离。
HINT 由于输入数据较大,C/C++中推荐使用scanf进行读入以获得更快的读入速度。同时请注意算法复杂度。
输入格式
输入的第一行是一个正整数T(T≤20),表示测试数据的组数。
每组输入数据的第一行是一个初始串S。第二行是一个正整数m(1≤m≤100000),表示总共操作的数量。接下来m行,每行表示一个操作。操作的格式如上所述。
数据保证在任何情况下,S的长度不会超过100000。
输出格式
对于每个QUERY,输出所求的最小距离。如果S中其它位置都不存在和它相同的字符,输出-1。
输入样例
2
axb
3
INSERT a
QUERY 0
QUERY 1
explore
3
INSERT r
QUERY 7
QUERY 1
输出样例
3 -1 2 -1
dp[pos[str[i]-'a']] = min(dp[pos[str[i]-'a']], i - pos[str[i]-'a']) ; dp[i] = i - pos[str[i]-'a'];
思路:dp[i]表示所求答案,则
pos 记录与当前字母相同的且离当前位置最近的字母的位置。
1 /* 2 USER_ID: test#wangzhili 3 PROBLEM: 94 4 SUBMISSION_TIME: 2014-04-02 22:19:32 5 */ 6 #include<iostream> 7 #include<cstdio> 8 #include<climits> 9 #include<cstring> 10 #define MAX 100005 11 using namespace std; 12 char str[MAX], op[20], cc[2]; 13 int pos[30], dp[MAX]; 14 int main(){ 15 int c, n, pp; 16 scanf("%d", &c); 17 while(c--){ 18 memset(str, 0, sizeof(str)); 19 memset(pos, -1, sizeof(pos)); 20 for(int i = 0;i < MAX;i ++) dp[i] = INT_MAX; 21 scanf("%s", str); 22 int len = strlen(str); 23 for(int i = 0;i < len;i ++){ 24 if(pos[str[i]-'a'] != -1){ 25 dp[pos[str[i]-'a']] = min(dp[pos[str[i]-'a']], i - pos[str[i]-'a']); 26 dp[i] = i - pos[str[i]-'a']; 27 } 28 pos[str[i]-'a'] = i; 29 } 30 scanf("%d", &n); 31 while(n--){ 32 memset(op, 0, sizeof(op)); 33 scanf("%s", op); 34 if(!strcmp("INSERT", op)){ 35 scanf("%s", cc); 36 str[len++] = cc[0]; 37 if(pos[cc[0]-'a'] != -1){ 38 dp[pos[cc[0]-'a']] = min(dp[pos[cc[0]-'a']], len-1-pos[cc[0]-'a']); 39 dp[len-1] = len-1-pos[cc[0]-'a']; 40 } 41 pos[cc[0]-'a'] = len-1; 42 }else{ 43 scanf("%d", &pp); 44 if(dp[pp] <= MAX) printf("%d ", dp[pp]); 45 else printf("-1 "); 46 } 47 } 48 } 49 return 0; 50 }