Java解PATA1093

1093 Count PAT’s (25 分)

The string APPAPT contains two PAT’s as substrings. The first one is formed by the 2nd, the 4th, and the 6th characters, and the second one is formed by the 3rd, the 4th, and the 6th characters.

Now given any string, you are supposed to tell the number of PAT’s contained in the string.

Input Specification:

Each input file contains one test case. For each case, there is only one line giving a string of no more than 105​​ characters containing only P, A, or T.

Output Specification:

For each test case, print in one line the number of PAT’s contained in the string. Since the result may be a huge number, you only have to output the result moded by 1000000007.

Sample Input:

APPAPT

Sample Output:

2

思路

这个题目的意思是让我们在一段长度不超过105只含有P、A、T三种字母的字符串序列中寻找顺序的PAT的个数,其中不要求PAT三个字母连续。
此题通过三重循环可以解出答案,但是由于运行限制时间为150ms,粗略计算时间复杂度约为O(n3),即大约需要计算1015次计算,而计算机一秒大约能执行5*108次计算,所以暴力算法肯定会超时。

于是试想能否用O(n)的复杂度的算法计算呢。

转换角度,PAT的个数等于A左边P的个数乘以A右边T的个数,于是可以用一个数组记录A第i位左边包括第i位上的P的个数。同样的方法用于查找T,从后往前查找T,在计算T的个数的同时,查找A,一旦找到A就开始累加该位左边P的总数与右边T的总数的乘积。

代码如下:

import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStreamReader;
import java.io.OutputStreamWriter;
import java.io.PrintWriter;
import java.util.StringTokenizer;

public class Main{

 static	int ans=0;
 static	int[] leftP;
 static int rightT=0;
 static int MOD=1000000007;

	static void search(String str){
		int len=str.length();
		for(int i=0;i<len;i++) {
			if(i==0) {
				if(str.charAt(i)=='P') leftP[i]=1;
			}else {
				if(str.charAt(i)=='P') {
					leftP[i]=leftP[i-1]+1;
				}
				else {
					leftP[i]=leftP[i-1];
				}
			}
		}
		
		for(int i=len-1;i>=0;i--) {
			char ch=str.charAt(i);
			if(ch=='T') {
						rightT++;
			}
			if(ch=='A') {
				ans=(ans+leftP[i]*rightT)%MOD;
			}
		}
		System.out.println(ans);
	

	}
	
	public static void main(String[] args) throws IOException {
		// TODO Auto-generated method stub
	//Scanner sc=new Scanner(System.in);
	
		BufferedReader reader=new BufferedReader(new 		  
		InputStreamReader(System.in));
		StringTokenizer strtoken= new StringTokenizer(reader.readLine());
		String str=strtoken.nextToken();
		leftP=new int[100010];
		for(int i=0;i<str.length();i++) {
			leftP[i]=0;
		}
		search(str);
	}
}

结果在这里插入图片描述

很开心看到ac后耗时并不多,这里采用的是BufferReader进行读入,使用Scanner真的很耗时,耗到不能通过…

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值