zoukankan      html  css  js  c++  java
  • hdu 5056(尺取法思路题)

    Boring count

    Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 32768/32768 K (Java/Others)
    Total Submission(s): 932    Accepted Submission(s): 382


    Problem Description
    You are given a string S consisting of lowercase letters, and your task is counting the number of substring that the number of each lowercase letter in the substring is no more than K.
     
    Input
    In the first line there is an integer T , indicates the number of test cases.
    For each case, the first line contains a string which only consist of lowercase letters. The second line contains an integer K.

    [Technical Specification]
    1<=T<= 100
    1 <= the length of S <= 100000
    1 <= K <= 100000
     
    Output
    For each case, output a line contains the answer.
     
    Sample Input
    3 abc 1 abcabc 1 abcabc 2
     
    Sample Output
    6 15 21
     
    Source
     
    题意:找出一个字符串里面符合每个字幕出现次数都不大于K次的子串的个数。
    题解:数据量达到了10^5,所以O(n^2)肯定不行,所以要用到尺取法。
    整个过程分为4布:

        1.初始化左右端点

        2.不断扩大右端点,直到满足条件

        3.如果第二步中无法满足条件,则终止,否则更新结果

        4.将左端点扩大1,然后回到第二步

    尺取法的过程是上述,但是,对于这题,我们要做少许改动,因为尺取法的条件终止条件是无法满足条件,但是这题我们首先扩充右端点的话是一直到不满足条件(找到某个字母出

    现次数大于K的那个串再break),所以这题我们的条件应该改成r在外层循环,找到无法满足条件的子串后再一直扩充左端点,直到满足条件。接下来怎么算子串个数呢?我也不知道

    ,discuss区里面这样说的。。

    队友的解释:
    #include <iostream>
    #include <stdio.h>
    #include <string.h>
    #include <algorithm>
    #include <stdlib.h>
    #include <math.h>
    using namespace std;
    typedef long long LL;
    const int N = 100005;
    int Hash[N],k;
    char str[N];
    bool judge(){
        for(int i=0;i<26;i++){
            if(Hash[i]>k) return false;
        }
        return true;
    }
    int main()
    {
        int tcase;
        scanf("%d",&tcase);
        while(tcase--){
            scanf("%s",str);
            scanf("%d",&k);
            int len = strlen(str);
            memset(Hash,0,sizeof(Hash));
            int l=0,r=0;
            LL cnt=0;
            while(r<len){
                Hash[str[r]-'a']++;
                while(l<len&&!judge()){
                    Hash[str[l]-'a']--;
                    l++;
                }
                if(!judge()) break;
                //printf("%d %d
    ",l,r);
                cnt =cnt+(r-l+1);
                r++;
            }
            printf("%lld
    ",cnt);
        }
        return 0;
    }
  • 相关阅读:
    sqlserver 自学笔记 函数实训 学分学期转换函数的设计
    jquery dom操作
    jquery clone方法
    Go开发常见陷阱
    Go 语言从新手到大神:每个人都会踩的五十个坑(转)
    Go文件操作大全
    linux下安装go
    Go 学习笔记
    分布式系统设计系列 -- 基本原理及高可用策略 (转)
    安装Redis图形监控工具---RedisLive
  • 原文地址:https://www.cnblogs.com/liyinggang/p/5652215.html
Copyright © 2011-2022 走看看