• 设计推特(Leetcode355)


    例题:

    https://leetcode.cn/problems/design-twitter/

    分析:

    推特其实类似于微博,在微博中可以发送文章。

    求解这类题目,我们需要根据题目需求,利用面向对象的思想,先对需求做一个抽象,看看能抽象出哪些对象。可以看出,题目中有3个对象:推特对象、用户对象、文章对象

    下图表示这3类对象之间的关系:

    我们知道,一个推特包含多个用户,推特和用户之间是一对多的关系,因此在推特类中可以创建一个map集合来保存用户数据;同样,一个用户可以发送多条文章,用户和文章也是一对多的关系,因为题目有一个方法,获取一个用户发送的近10条文章(其中包括关注者发送的),我们可以用一个链表来存储推文,在用户类中设置一个头节点。

    一个用户也可以关注多个用户,用户与用户之间也是一对多的关系,可以用一个set集合存储关注的用户。

    这里面有个方法getNewsFeed()获取最新的10篇文章, 包括自己发送的和关注者发送的,其实这就是一个多链表合并问题,按推文时间合并,可以采用大顶堆的方式把自己的推文和关注者的推文加入堆中,然后从堆中弹出一个最近的文章,然后再加入该链表的下一篇推文。

            ​​​​​     ​ 

    如上图,假设①号链表 表示用户的推文,其它链表是关注者的推文,首先依次把 各链表的头节点加入堆中(10, 9, 3),在堆中弹出一篇最近的文章(10)。紧接着加入被弹出链表的下一个节点(6),再和其它链表头的元素相比选出最近的,依次类推。

    代码实现:
    1. package leetcodeup;
    2. import java.util.*;
    3. public class TwitterLeetcode355 {
    4. static class Twitter {
    5. public Twitter() {
    6. }
    7. static class Tweet{
    8. int tweetId;
    9. int time;
    10. Tweet next;
    11. public Tweet(int tweetId, int time, Tweet next) {
    12. this.tweetId = tweetId;
    13. this.time = time;
    14. this.next = next;
    15. }
    16. public int getTweetId() {
    17. return tweetId;
    18. }
    19. public int getTime() {
    20. return time;
    21. }
    22. }
    23. static class User{
    24. int userId;
    25. public User(int userId) {
    26. this.userId = userId;
    27. }
    28. Tweet head = new Tweet(-1, -1, null);
    29. Set followees = new HashSet<>();
    30. }
    31. private final Map userMap = new HashMap<>();
    32. private static int time;
    33. //发布文章
    34. public void postTweet(int userId, int tweetId) {
    35. User user = userMap.computeIfAbsent(userId, User::new);
    36. user.head.next = new Tweet(tweetId, time++, user.head.next);
    37. }
    38. //新增关注
    39. public void follow(int followerId, int followeeId) {
    40. User user = userMap.computeIfAbsent(followerId, User::new);
    41. User followee = userMap.computeIfAbsent(followeeId, User::new);
    42. user.followees.add(followee.userId);
    43. }
    44. //取消关注
    45. public void unfollow(int followerId, int followeeId) {
    46. User user = userMap.get(followerId);
    47. if(user != null){
    48. user.followees.remove(followeeId);
    49. }
    50. }
    51. //获取最新的10篇文章(包括自己和关注者)
    52. public List getNewsFeed(int userId) {
    53. PriorityQueue queue = new PriorityQueue<>(Comparator.comparingInt(Tweet::getTime).reversed());
    54. User user = userMap.get(userId);
    55. if(user == null){
    56. return List.of();
    57. }
    58. if(user.head.next != null){
    59. queue.offer(user.head.next);
    60. }
    61. Set followees = user.followees;
    62. for (Integer id : followees) {
    63. User followee = userMap.get(id);
    64. if(followee.head.next != null){
    65. queue.offer(followee.head.next);
    66. }
    67. }
    68. List res = new ArrayList<>();
    69. int count = 0;
    70. while(!queue.isEmpty() && count < 10){
    71. Tweet tweet = queue.poll();
    72. res.add(tweet.tweetId);
    73. if(tweet.next != null){
    74. queue.offer(tweet.next);
    75. }
    76. count++;
    77. }
    78. return res;
    79. }
    80. }
    81. }

  • 相关阅读:
    Go学习第三章——运算符与进制
    数据结构——排序算法——归并排序
    无代码编程时代的到来:新兴工具和平台的前瞻展望
    850. 矩形面积 II--(每日一难phase--day16)
    带你玩转CompletableFuture异步编程
    年仅 16 岁的黑客少年,竟是搅乱 IT 巨头的幕后主使?
    【尚硅谷 Vue学习】P18姓名案例 P19 计算属性 p20计算属性_简写 P21天气案例
    【电源专题】案例:电源芯片对输入索取大电流的异常开发板测试能出现,但整机就无法复现?
    推荐两款HTTP请求Mock利器
    vue 使用openlayers导出渲染的地图
  • 原文地址:https://blog.csdn.net/qq_63748940/article/details/136279148