AcwingP1238-日志统计

import java.util.*;

public class Main {
	public static void main(String[] args) {
		Scanner scan = new Scanner(System.in);
		//输入n,d,k;
		int n = scan.nextInt();
		int d = scan.nextInt();
		int k = scan.nextInt();
		//创建R类型数组,将输入的各个R对象存入
		R[] rs = new R[n];
		for(int i = 0;i < n;i ++) {
			R r = new R();
			r.st = scan.nextInt();
			r.sd = scan.nextInt();
			rs[i] = r;
		}
		//将数组中的记录,按照st进行升序排序
		//匿名内部类进行排序
		Arrays.sort(rs,new Comparator<R>() {
			@Override
			public int compare(R r1,R r2) {
				// TODO Auto-generated method stub
				return r1.st - r2.st;
			}
		});
		
		//记录每次sd出现的次数
		//用hashMap来存入sd的数量,因为它通过键值对,且不重复;键是id,值是id出现的次数
		Map<Integer,Integer> cnt = new HashMap<>();
		//记录存放结果
		//new TreeSet<>():是创建一个TreeSet实例的语句。
		//TreeSet是SortedSet接口的一个实现类,它使用红黑树数据结构来存储元素,可以保证元素的有序性
		//它的特点是不允许存储重复的元素。当向TreeSet中添加一个已经存在的元素时,该元素不会被添加到集合中,也不会抛出异常。
		SortedSet<Integer> answers = new TreeSet<>();
		//对排好序的数组进行双指针遍历
		int j = 0;
		for(int i = 0;i < n;i ++) {
			while(j < n && rs[j].st - rs[i].st < d) {//j从sd遍历,当j<n并且日期<d进行遍历,因为当日期差大于等于d,便不是热帖
				Integer s = rs[j].sd;
				if(cnt.get(s) != null) {//判断sd是否已经存在。若不存在,则赋值·1,若存在,则加1
					cnt.put(s, cnt.get(s) +1);
				}else {
					cnt.put(s, 1);//第一次出现
				}
				if(cnt.get(s) >= k) {//若在k天内,达到k次,便是热搜,直接存进结果中
					answers.add(s);
				}
				j ++;
			}
			//当i向下遍历的时候,在i没有改变之前,如过cnt中i对应的值,不为空,应当-1,因为他已经超出d的范围了
			if(cnt.get(rs[i].sd) != null) {
				cnt.put(rs[i].sd,cnt.get(rs[i].sd) - 1);
			}
			
		}
		for(Integer i: answers) {
			System.out.println(i);
		}
	}
	//将st,sd捆绑起来
	 static class R{
		int st;
		int sd;
	}

}

  • 8
    点赞
  • 9
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值