用三个散列分别记录PAT的位置,根据确定某一位置的A所能组成的pat的个数为A左侧的P的个数 乘以 A右侧的T的个数, 进行A的历遍。
如果根据P A T三个慢慢历遍肯定会超时。我还尝试用二分法分别找第一个在A右侧的P和T,也超时了。还是找用递推的方法省时间。
#include <cstdio>
#include <vector>
#include <string.h>
#include <algorithm>
#include <math.h>
#include <iostream> //用set试试
using namespace std;
int upper_b(int x,vector<int> vec,int left,int right,int flag){
if(flag){
if(x<vec[left]){
return -1;
}
}else{
if(x>vec[right]){
return -1;
}
}
while(left<right){
int mid=(right-left)/2+left;
if(vec[mid]<x){
left=mid+1;
}else{
right=mid;
}
}
return left;
}
int main(){
string str;
vector<int>hashtableP;
vector<int>hashtableA;
vector<int>hashtableT;
getline(cin,str);
int i=0,j=0,k=0,cnt=0,P=0,T=0;
int len =str.size();
for(i=0; i<len; i++){
switch(str[i]){
case 'P': hashtableP.push_back(i);
break;
case 'A': hashtableA.push_back(i);
break;
case 'T': hashtableT.push_back(i);
};
}
int len1=hashtableP.size();
int len2=hashtableA.size();
int len3=hashtableT.size();
i=0;
for(j=0; j<len2; j++){
int x = hashtableA[j];
while(hashtableP[i]<x && i<len1){
i++;
}
while(hashtableT[k]<x && k<len3){
k++;
}
cnt=(cnt+i*(len3-k))%1000000007;
}
printf("%d",cnt);
return 0;
}
转载须注明出处。