题意

AraBellaC

Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 65536/65536 K (Java/Others)
Total Submission(s): 277    Accepted Submission(s): 100


Problem Description
Princess Arabella loves the letter `C`, which earned her the epithet `ArraBellaC`. She would like to endeavor to construct a periodic string with length n(n≤20000) to spare her tedious time. In every period of the string, the substring begins with dozens of `A`s and ends with dozens of `C`s, and dozens of `B`s are inserted between them, and the number of `A`, `B`, `C` is a, b, c.(For example, if a=1, b=1, c=2 then one of the period of the string is `ABCC`, and the periodic string is `ABCCABCC……`).Note that in the last period of the string, the substring can be incomplete and the last few letters of the period can be cut down.

And now, Arabella has constructed a periodic string, she want to give you a question: if she tells you the character is Ci(Ci∈{A,B,C}) in the Xi(Xi≤10000) , then could you tell her the value of a,b,c? If there are multiple answers, please find the lexicographically smallest answer. If you can’t find a valid answer, please print `NO`
 

Input
The first line gives an integer T(1≤T≤40) , which indicates the number of cases in the input.
The first line of every case contains only one integer m(1≤m≤5000), which means the number of characters AraBella told you.
A number Xi(1≤Xi≤10000) and a letter Ci are given in the following m lines, which means the position Xi in the string with letter Ci.
 

Output
Print a,b,c in order. If there are multiple answers, please find the lexicographically smallest answer. If you can’t find a valid answer, please print `NO`.(It is gratuated that 0<a,b,c, and please forget my poor Yinglish)
 

Sample Input
2 3 1 A 2 B 3 C 4 1 A 2 C 3 B 4 C
 

Sample Output
1 1 1 NO
 

Source
 

Recommend
chendu
 

Statistic | Submit | Discuss | Note

分析

参照616156的题解。

题解又在卖萌了。。要用RMQ?。。。估计他自己没想清楚吧。。。这题哪用得着RMQ啊。。。

首先,可以暴力枚举循环节的长度:
然后,对每种字母进行判断,求出每个循环节中B,C最靠前的位置和A,B最靠后的位置。
如果A最靠后的位置在B最靠前的后面,或者B最靠后的位置在C最靠前的后面。就说明当前这个循环节长度是矛盾的。

如果不矛盾,则将A最靠后的位置及以前,都设为A,B最靠后的位置及以前(除去A的部分)都设为B,C则填充这个循环节剩余的位置。就能保证是当前长度循环节中,答案字典序最小一种方案。

问题就在于如何处理:“每个循环节中B,C最靠前的位置和A,B最靠后的位置”
可以利用调和级数:暴力枚举每个循环节,O(1)求出当前循环节最靠前的B、C,最靠后的A、B。总的时间复杂度就是O(N ln N)。

题解的方法说要用RMQ求这个问题。。。
其实就用前缀和后缀的思想不就行了?

对于每个点,它前面最近的一个A、B字母的位置,以及它后面最靠近的一个B、C字母的位置。这两个东西可以O(N)递推求出来

询问某个循环节时,求出其左端点及以后,最靠前的B、C,以及其右端点及以前最靠后的A、B即可(就是上面维护的那两个东西)。

代码

#include<bits/stdc++.h>
#define rg register
#define il inline
#define co const
template<class T>il T read(){
    rg T data=0,w=1;
    rg char ch=getchar();
    while(!isdigit(ch)){
        if(ch=='-') w=-1;
        ch=getchar();
    }
    while(isdigit(ch))
        data=data*10+ch-'0',ch=getchar();
    return data*w;
}
template<class T>il T read(rg T&x){
    return x=read<T>();
}
typedef long long ll;
using namespace std;
co int N=1e4;
int a[N+10],pre[N+10][4],las[N+10][4],ans[4],ans1[4];
char s[20];
int get_pre(int len,int x){
    int res=len;
    for(int i=1;i<=N;i+=len){
        int t=las[i][x];
        if(t>=i+len) continue;
        res=min(res,t-i+1);
    }
    return res;
}
int get_las(int len,int x){
    int res=0;
    for(int i=1;i<=N;i+=len){
        int top=min(i+len-1,N);
        int t=pre[top][x];
        if(t<i) continue;
        res=max(res,t-i+1);
    }
    return res;
}
int main(){
//  freopen(".in","r",stdin),freopen(".out","w",stdout);
    int kase=read<int>();
    while(kase--){
        int m=read<int>();
        memset(ans,-1,sizeof ans);
        memset(a,0,sizeof a);
        memset(pre,0,sizeof pre);
        memset(las,0x3f,sizeof las);
        for(int i=1,pos;i<=m;++i){
            read(pos);scanf("%s",s);
            a[pos]=s[0]-'A'+1;
        }
        for(int i=1;i<=N;++i)
            for(int j=1;j<=3;++j){
                if(a[i]==j) pre[i][j]=i;
                pre[i][j]=max(pre[i][j],pre[i-1][j]);
            }
        for(int i=N;i>=1;--i)
            for(int j=1;j<=3;++j){
                if(a[i]==j) las[i][j]=i;
                las[i][j]=min(las[i][j],las[i+1][j]);
            }
        for(int len=3;len<=N;++len){
            int lasx=0;
            bool flag=0;
            for(int j=1;j<=3;++j){
                if(j!=1){
                    int prex=get_pre(len,j);
                    if(prex<=lasx) {flag=1;break;}
                }
                if(j!=3){
                    lasx=max(lasx+1,get_las(len,j));
                    ans1[j]=lasx;
                }
                else ans1[j]=len;
            }
            if(flag==0){
                for(int j=1;j<=3;++j){
                    if(ans1[j]<ans[j]||ans[j]==-1){
                        ans[1]=ans1[1],ans[2]=ans1[2],ans[3]=ans1[3];
                        break;
                    }
                    if(ans1[j]>ans[j]) break;
                }
            }
        }
        if(ans[1]!=-1) printf("%d %d %d\n",ans[1],ans[2]-ans[1],ans[3]-ans[2]);
        else puts("NO");
    }
    return 0;
}

HDU6387 AraBellaC的更多相关文章

  1. 2018 Multi-University Training Contest 7 Solution

    A - Age of Moyu 题意:给出一张图,从1走到n,如果相邻两次走的边的权值不同,花费+1, 否则花费相同,求最小花费 思路:用set记录有当前点的最小花费有多少种方案到达,然后最短路 #i ...

随机推荐

  1. FASTQ 数据质量统计工具

    主流工具: FastQC fqcheck readfq 拿到测序数据的第一步就是做质量控制 fqcheck之后得到的结果: 它会统计每条reads,按read 1-100位点计算每个位置的ACGTN含 ...

  2. WPF几种高级绑定

    (1)Binding  + RelativeSource + AncestorType 模式  , 根据关联源所指定的类型,可动态绑定指定类型的Path属性(Path可以省略)(PS:动态指父级在运行 ...

  3. English trip -- Phonics 5 元音字母 o

    Vowel 元音 元音 O Consonant 辅音 清辅音   h    wh 浊辅音  m    wh  n   ng   y oa:[əʊ]  # 字母本身音 coat boat load co ...

  4. vue.js 过渡&动画

    9-17 在add ,update, remove DOM时 提供多种方式的应用过度效果. 包括以下可选工具:(2大类,css和js) 在css过度和动画中自动应用class 配合使用第三方css动画 ...

  5. JSP页面出现乱码

    Jsp文件中会出现下面所示的编码指定方式: <%@ page language="java" contentType="text/html; charset=UTF ...

  6. 新项目中使用的linux命令

    要通过跳板机进入内网之后,访问内网域名 mysql -h xxxxxxx -u u_caojiangjiang -p -P 3306 上传文件: scp -r /Users/qudian/Deskto ...

  7. CSS样式属性——背景

     背景——包括背景颜色.背景图片,以及背景图片的控制 background-color:设置背景色(transparent表示透明的背景色) background-image:设置元素的背景图片 ba ...

  8. length,lengthb,substr,substrb,instr小用

    --字符串的字符长度 select length('wm.dfw.士农工商.sda.人马ss.dfw.4.sdf.332.sf.qq.sd') from dual; --字符串的字节长度 select ...

  9. SQL基础用法(实例二)

    /* 2006年10月01日 SQL Server 数据库的高级操作 (1) 批处理 (2) 变量 (3) 逻辑控制 (4) 视图 (5) 函数 (6) 高级查询 */ ()批处理 将多条SQL语句作 ...

  10. httpclient 相关使用介绍

    httpclient中sessionId的获取与设置 public class HttpSessionId { public static void main(String[] args) throw ...