zoukankan      html  css  js  c++  java
  • HDU

    Mr. Frog has two sequences a1,a2,⋯,an and b1,b2,⋯,bm and a number p. He wants to know the number of positions q such that sequence b1,b2,⋯,bm is exactly the sequence aq,aq+p,aq+2p,⋯,aq+(m−1)p where q+(m−1)p≤n and q≥1

    Input

    The first line contains only one integer T≤100

    , which indicates the number of test cases.

    Each test case contains three lines.

    The first line contains three space-separated integers 1≤n≤106,1≤m≤106 and 1≤p≤106.

    The second line contains n integers a1,a2,⋯,an(1≤ai≤109).

    the third line contains m integers b1,b2,⋯,bm(1≤bi≤109)

    Output

    For each test case, output one line “Case #x: y”, where x is the case number (starting from 1) and y is the number of valid q’s.

    Sample Input

    2
    6 3 1
    1 2 3 1 2 3
    1 2 3
    6 3 2
    1 3 2 2 3 1
    1 2 3

    Sample Output

    Case #1: 2
    Case #2: 1

    题解:

    直接把多个串拿出来单独跑KMP。

    代码:

    #include <bits/stdc++.h>
    
    using namespace std;
    
    const int MAXN = 1e6+10;
    
    int A[MAXN];
    int B[MAXN];
    int C[MAXN];
    int next1[MAXN];
    
    void getNext(int M){
    
        int k = -1;
        int j = 0;
        next1[0] = -1;//next数组最好是从0开始要不然会很麻烦 
        while(j<M){
            if(k == -1 || B[j] == B[k]){
                if(B[j+1] == B[k+1]){ 
                    next1[++j] = next1[++k];
                }
                else next1[++j] = ++k;
            }
            else {
                k = next1[k];
            }
        }
    }
    
    int Find(int N,int M,int st){//返回匹配到的位置 
        int temp1 = st,temp2 = 0;
        while(temp1<N && temp2<M){
            if(temp2 == -1 || C[temp1] == B[temp2]){
                temp1++;temp2++;
            }
            else{
                temp2 = next1[temp2];
            }
        } 
        if(temp2 == M)return temp1-temp2;
        else return -1;  
    }
    
    
    int main(){
    	
    	int T,N,M,P;
    	scanf("%d",&T);
    	for(int _=1 ; _<=T ; ++_){
    		scanf("%d %d %d",&N,&M,&P);
    		for(int i=0 ; i<N ; ++i)scanf("%d",&A[i]);
    		for(int i=0 ; i<M ; ++i)scanf("%d",&B[i]);
    		int num,sum = 0;
    		getNext(M);
    		for(int i=0 ; i<P ; ++i){
    			num = 0;
    			for(int j = i;j < N && i+(M-1)*P < N;j += P)C[num++] = A[j];
               	int t = Find(num,M,0);
               	while(t != -1){
               		++sum;
    				t = Find(num,M,t+1);	
    		   	}
    		}
    		printf("Case #%d: %d
    ",_,sum);
    	}
    	
    	return 0;
    } 
  • 相关阅读:
    Nokia N8手机上开发Qt应用程序第一步:配置手机,使其支持Qt应用程序的运行
    Visual Studio 2010 "工具">"选项"中的VC++目录编辑功能已被否决
    删除用户 ORA04098
    把Excel转换成DataTable
    可编辑的DIV
    RDLC 错误号.
    leetcode| Add Digits
    leetcode| Integer to English Words
    leetcode|Counting Bits
    锁表了。。。
  • 原文地址:https://www.cnblogs.com/vocaloid01/p/9514041.html
Copyright © 2011-2022 走看看