2018年第九届蓝桥杯 第八题:日志统计(满分21分)

标题:日志统计
小明维护着一个程序员论坛。现在他收集了一份"点赞"日志,日志共有N行。其中每一行的格式是:
ts id 
表示在ts时刻编号id的帖子收到一个"赞"。 
现在小明想统计有哪些帖子曾经是"热帖"。如果一个帖子曾在任意一个长度为D的时间段内收到不少于K个赞,小明就认为这个帖子曾是"热帖"。 
具体来说,如果存在某个时刻T满足该帖在[T, T+D)这段时间内(注意是左闭右开区间)收到不少于K个赞,该帖就曾是"热帖"。 
给定日志,请你帮助小明统计出所有曾是"热帖"的帖子编号。 
【输入格式】
第一行包含三个整数N、D和K。 
以下N行每行一条日志,包含两个整数ts和id。 
对于50%的数据,1 <= K <= N <= 1000 
对于100%的数据,1 <= K <= N <= 100000 0 <= ts <= 100000 0 <= id <= 100000 
【输出格式】
按从小到大的顺序输出热帖id。每个id一行。 
【输入样例】
7 10 2 
0 1 
0 10   
10 10 
10 1 
9 1
100 3 
100 3 
【输出样例】


资源约定:
峰值内存消耗(含虚拟机) < 256M
CPU消耗  < 1000ms
 
解题思路:
构造一个二维数组,数组的行对应每个帖子的 id,可以用行下标和帖子id进行关联。每行的内容记录点赞的实际ts。
对数组的每行排序,按照ts值从小到大排序。
对每一行,滑动起始位置,找到到达K个赞的结束位置,取出两个端点的时间,计算时间差看是否满足小于D。
 1 #include <iostream>
 2 #include <vector>
 3 #include <algorithm>
 4 using namespace std;
 5 const long int NUM = 100000;  
 6 vector< vector<int> >  v_ids(NUM+1);
 7 int N,D,K;
 8 
 9 bool check(vector<int> v){
10     int j=0;
11     int r=j+K-1;
12     bool flag = false;
13     while(r<v.size()){
14         if(v[r]-v[j] < D){
15             flag = true;
16             break;
17         }
18         else{
19             j++;
20             r=j+K-1;
21         }
22     }
23     return flag;    
24 }
25 
26 int main(){
27     cin>>N>>D>>K;    
28     int ts,id;
29     int i;
30     for(i=0;i<N;i++){
31         cin>>ts>>id;
32         v_ids[id].push_back(ts);
33     }
34     for(i=0;i<=NUM;i++){
35         if( !v_ids[i].empty() ){
36             sort(v_ids[i].begin(),v_ids[i].end());
37             if (check(v_ids[i]))
38                 cout<<i<<endl;
39         }
40     }
41 }
using vector
原文地址:https://www.cnblogs.com/candyYang/p/10521655.html