zoukankan      html  css  js  c++  java
  • 12174

      You are listening to your music collection using the shuffle function to keep the music surprising. You
    assume that the shuffle algorithm of your music player makes a random permutation of the songs in
    the playlist and plays the songs in that order until all songs have been played. Then it reshuffles and
    starts playing the list again.
      You have a history of the songs that have been played. However, your record of the history of played
    songs is not complete, as you started recording songs at a certain point in time and a number of songs
    might already have been played. From this history, you want to know at how many different points in
    the future the next reshuffle might occur.
      A potential future reshuffle position is valid if it divides the recorded history into intervals of length
    s (the number of songs in the playlist) with the rst and last interval possibly containing less than s
    songs and no interval contains a specic song more than once.
    Input
    On the rst line one positive number: the number of testcases, at most 100. After that per testcase:
    • One line with two integers s and n (1 ≤ s, n ≤ 100000): the number of different songs in the
    playlist and the number of songs in the recorded playlist history.
    • One line with n space separated integers, x1, x2, . . . , xn (1 ≤ xi ≤ s): the recorded playlist history.
    Output
    Per testcase:
    • One line with the number of future positions the next reshuffle can be at. If the history could
    not be generated by the above mentioned algorithm, output 0.
    Sample Input
    4
    4 10
    3 4 4 1 3 2 1 2 3 4
    6 6
    6 5 4 3 2 1
    3 5
    3 3 1 1 1
    7 3
    5 7 3
    Sample Output
    1
    6
    0
    7

    题意理解:

      给定长度为n的播放历史记录,推断下一次重排的时间点的可能情况数目。注意首尾两段的记录允许不完整(小于s)。

      特殊情况:当n<s时,如果记录中的每首歌均无重复,比如:

      7 3

      5 7 3

      5号歌之前可能还存在1~7(大于7时的情况是等效的)首歌已经播放却没有加入记录,那么下一次重排点就有这7种情况。

    解题思路:

      使用滑动窗口的思想进行预处理:对n中的第i个数,如果紧随其后的s个数均没有重复,那么以i为起始的窗口是合法的。 

      

     1 #include <iostream>
     2 #include <cstdio>
     3 #include <cstring>
     4 #include <ctime>
     5 #include <set>
     6 #define time_ printf("time = %f
    ",double(clock())/CLOCKS_PER_SEC)
     7 using namespace std;
     8 const int maxn=100000;
     9 int s,n;
    10 int seq[maxn+5];
    11 int num[maxn+5];
    12 int id[maxn+5];
    13 
    14 void pre_process(){
    15     int l=0,r=0;
    16     memset(num,0,sizeof num);
    17     memset(id,0,sizeof id);
    18     int single=0;
    19     for(;r<l+s&&r<n;r++){
    20         int id=seq[r];
    21         num[id]++;
    22         if(num[id]==1) single++;
    23         else single--;
    24     }
    25     if(single==r-l) id[l]=1;
    26     while(l<n){
    27         int a=seq[l];
    28         int b=seq[r];
    29         num[a]--;
    30         if(num[a]==0) single--;
    31         if(num[a]==1) single++;
    32         l++;
    33         if(r!=n){
    34             num[b]++;
    35             if(num[b]==1) single++;
    36             if(num[b]==2) single--;
    37             r++;
    38         }
    39         if(l!=n&&single==r-l) id[l]=1;
    40     }
    41 }
    42 int main(int argc, const char * argv[]) {
    43     int T;
    44     scanf("%d",&T);
    45     while(T--){
    46         scanf("%d%d",&s,&n);
    47         for(int i=0;i<n;i++)
    48             scanf("%d",&seq[i]);
    49         pre_process();
    50         int ans=0;
    51         int rst[maxn+5];
    52         memset(rst,0,sizeof rst);
    53         rst[seq[0]]++;
    54         int single=1;
    55         for(int d=1;d<=s&&d<=n;d++){
    56             bool ok=true;
    57             if(single!=d) break;;
    58             for(int pt=d;pt<n;pt+=s){
    59                 if(id[pt]==0){
    60                     ok=false;
    61                     break;
    62                 }
    63             }
    64             if(ok) ans++;
    65             rst[seq[d]]++;
    66             if(rst[seq[d]]==1) single++;
    67         }
    68         if(n<s&&ans==n)
    69             ans=s;
    70         printf("%d
    ",ans);
    71     }
    72     return 0;
    73 }
  • 相关阅读:

    tomcat 和jboss区别
    python好文章
    CUBRID学习笔记 34 net参数化查询 cubrid教程示例
    CUBRID学习笔记 33 net事务 cubrid教程示例
    CUBRID学习笔记 32 对net的datatable的支持 cubrid教程
    CUBRID学习笔记 31 通过select创建表
    CUBRID学习笔记 30 复制表结构 cubrid教程
    CUBRID学习笔记 29 web管理中文语言文件 CUBRID教程
    CUBRID学习笔记 28 执行sql脚本文件
  • 原文地址:https://www.cnblogs.com/Kiraa/p/5488108.html
Copyright © 2011-2022 走看看