• 博客园logo
  • 会员
  • 众包
  • 新闻
  • 博问
  • 闪存
  • 赞助商
  • HarmonyOS
  • Chat2DB
    • 搜索
      所有博客
    • 搜索
      当前博客
  • 写随笔 我的博客 短消息 简洁模式
    用户头像
    我的博客 我的园子 账号设置 会员中心 简洁模式 ... 退出登录
    注册 登录

xxxqqq

  • 博客园
  • 联系
  • 订阅
  • 管理

View Post

实时输出topk最频繁变动的股价

网上看到了一道关于bloomburg的面试题,follow 评论的思路 自己试着写了一个HashHeap的实现。

基本思路是维护一个大小为K的最小堆,里面是topK股价变动的公司ID(假设ID是Integer)

HashHeap中维护一个companyIdHeap 之外还有一个HashMap 它的key 是CompanyId, value是Company信息 此处我假设company信息包含这个company在companyIdHeap中的index (这个index可以使delete function的复杂度降到O(logK))和它的股价变化了多少次

每当有新的估价更新,假设应用会调用HashHeap的add函数 输入是当前股价变化的公司ID 然后更新 hashmap 和 根据当前heap size更新companyIdHeap

在更新companyIdHeap的时候 如果这个变化的公司的股价变化次数大于最小堆的root 那么替换掉这个root 然后从0向下调整heap heap调整的比较条件是看谁的股价变化次数少

delete函数直接delete掉一个company O(logK)

poll函数是给heap root的company的股价变化次数减一(其实还没想好这个函数具体应该做什么 暂时把它放在注释里面)

不足之处请指出! 多谢!

 

  1 package Heap;
  2 
  3 import java.util.*;
  4 
  5 public class HashHeap {
  6     //a list of companyId
  7     private List<Integer> companyIdHeap;
  8     private int size_t;
  9     //map from companyId to Node {index in heap and frequent}
 10     private Map<Integer, Node> companyToFrequent;
 11     private String mode; //min or max
 12     private int K;
 13     class Node{
 14         public int index;
 15         public int frequent;
 16         public Node (int index, int fre){
 17             this.index= index;
 18             this.frequent = fre;
 19         }
 20         public Node(Node node){
 21             this.index = node.index;
 22             this.frequent = node.frequent;
 23         }
 24     }
 25     
 26     public HashHeap(int K){
 27         this.companyIdHeap = new ArrayList<Integer>();
 28         this.size_t =0;
 29         this.companyToFrequent = new HashMap<Integer, Node>();
 30         mode = "min";
 31         this.K = K;
 32     }
 33     
 34     public int peek(){
 35         if(!companyIdHeap.isEmpty())
 36             return companyIdHeap.get(0);
 37         return -1;
 38     }
 39     
 40     public int size(){
 41         return size_t;
 42     }
 43     
 44     public boolean empty(){
 45         return companyIdHeap.size()==0;
 46     }
 47     
 48     public int parent(int id){
 49         if(id==0){
 50             return -1;
 51         }
 52         return (id-1)/2;
 53     }
 54     
 55     public int lson(int id){
 56         return 2*id +1;
 57     }
 58     
 59     public int rson(int id){
 60         return 2*id+2;
 61     }
 62     
 63     public boolean compare(int companyA, int companyB){
 64         if(companyToFrequent.get(companyA).frequent<companyToFrequent.get(companyB).frequent){
 65             if(mode.equals("min")){
 66                 return true;
 67             }else{
 68                 return false;
 69             }
 70         }else{
 71             if(mode.equals("min")){
 72                 return false;
 73             }else{
 74                 return true;
 75             }
 76         }
 77     }
 78     
 79     public void swap(int indexA, int indexB){
 80         int companyA = companyIdHeap.get(indexA);
 81         int companyB = companyIdHeap.get(indexB);
 82         Node compNodeA = companyToFrequent.get(companyA);
 83         Node compNodeB = companyToFrequent.get(companyB);
 84         companyIdHeap.set(indexA, companyB);
 85         companyIdHeap.set(indexB, companyA);
 86         companyToFrequent.put(companyA, new Node(indexB, compNodeA.frequent));
 87         companyToFrequent.put(companyB, new Node(indexA, compNodeB.frequent));
 88     }
 89     
 90     public void siftup(int index){
 91         while(parent(index)>-1){
 92             int parent = parent(index);
 93             if(compare(companyIdHeap.get(parent), companyIdHeap.get(index))){
 94                 break;
 95             }else{
 96                 swap(parent, index);
 97             }
 98             index = parent;
 99         }
100     }
101     
102     public void siftdown(int index){
103         while(lson(index)< companyIdHeap.size()){
104             int leftSon = lson(index);
105             int rightSon = rson(index);
106             int son = rightSon;
107             if(rightSon>=companyIdHeap.size()||compare(companyIdHeap.get(leftSon),companyIdHeap.get(rightSon))){
108                 son = leftSon;
109             }
110             if(compare(companyIdHeap.get(index), companyIdHeap.get(son))){
111                 break;
112             }else{
113                 swap(index, son);
114             }
115             index=son;
116         }
117         
118     }
119     
120     public void add(int company){
121         //update hashmap
122         if(companyToFrequent.containsKey(company)){
123             Node node = companyToFrequent.get(company);
124             companyToFrequent.put(company, new Node(node.index, node.frequent+1));
125         }else{
126             companyToFrequent.put(company, new Node(-1, 1));
127         }
128         //update heap
129         Node node = companyToFrequent.get(company);
130         if(this.size_t==K){
131             //if heap need to be updated
132             if(compare(peek(), company)){
133                 companyIdHeap.set(0, company);
134                 companyToFrequent.put(company, new Node(0, node.frequent));
135                 siftdown(0);
136             }
137             return;
138         }
139         companyIdHeap.add(company);
140         size_t++;
141         companyToFrequent.put(company, new Node(companyIdHeap.size()-1, node.frequent));
142         siftup(companyIdHeap.size()-1);
143     }
144 
145     public void delete(int company){
146         if(companyToFrequent.containsKey(company)){
147             Node node = companyToFrequent.get(company);
148             int index = node.index;
149             swap(index, companyIdHeap.size()-1);
150             companyIdHeap.remove(companyIdHeap.size()-1);
151             companyToFrequent.remove(company);
152             size_t--;
153             //the condition will be false if index == companyIdHeap.size()-1 before
154             if(index<companyIdHeap.size()){
155                 siftup(index);
156                 siftdown(index);
157             }
158         }
159     }
160 
161     /*public int poll(){
162         int res = companyIdHeap.get(0);
163         Node node = companyToFrequent.get(res);
164         if(node.frequent==1){
165             size_t--;
166             swap(0, companyIdHeap.size()-1);
167             companyIdHeap.remove(companyIdHeap.size()-1);
168             companyToFrequent.remove(res);
169             // the condition will be true is companyIdHeap.size() == 1 before
170             if(companyIdHeap.size()>0){
171                 siftdown(0);
172             }
173         }else{
174             companyToFrequent.put(res, new Node(0, node.frequent-1));
175         }
176         
177         return res;
178     }*/
179 }

 

posted on 2017-05-11 05:50  xxxqqq  阅读(367)  评论(0)    收藏  举报

刷新页面返回顶部
 
博客园  ©  2004-2025
浙公网安备 33010602011771号 浙ICP备2021040463号-3