美文网首页
[295]find median from data strea

[295]find median from data strea

作者: 秋_轩 | 来源:发表于2017-01-05 10:50 被阅读0次

    leetcode

    two heap

    use two heap is quite straight forward.

    import java.util.Comparator;
    import java.util.PriorityQueue;
    
    public class MedianFinder {
        PriorityQueue<Integer> left;
        PriorityQueue<Integer> right;
    
        MedianFinder(){
            left = new PriorityQueue<>(10, new Comparator<Integer>() {
                @Override
                public int compare(Integer o1, Integer o2) {
                    return o2 - o1;
                }
            });
            right = new PriorityQueue<>();
        }
    
    
        // Adds a number into the data structure.
        public void addNum(int num) {
            if(left.size() == 0)left.add(num);
    
            else{
                if(num < left.peek()){
                    left.add(num);
                } else {
                    right.add(num);
                }
            }
            if(right.size() > left.size())left.offer(right.poll());
    
            if(left.size() > right.size() + 1){
                right.offer(left.poll());
            }
    
        }
    
        // Returns the median of current data stream
        public double findMedian() {
            if(left.size() == right.size()){
                return (left.peek() + right.peek()) / 2.0;
            }
            else return left.peek();
    
        }
    
    
    }
    
    // Your MedianFinder object will be instantiated and called as such:
    // MedianFinder mf = new MedianFinder();
    // mf.addNum(1);
    // mf.findMedian();
    

    use binary tree

    Use the binary search tree to maintain the structure.
    Each add operation, insert the number into BST.

    So "find median" is the same task as the "select" operation, which has something to do with the rank.

    you can see the algo slides from Princeton for a clear view:
    princeton slides

    The idea to implement that is to maintain a variable for each node, to record the size of left child.

    
    
    
    
    
    public class MedianFinder {
        Tree tree;
    
        class Tree{
            TreeNode root;
            int total;
    
            public void display(TreeNode root){
                if(root == null) System.out.print("# ");
                else {
                    System.out.print(root.val + " " );
                    display(root.left);
                    display(root.right);
                }
            }
    
            public void insert(int num){
                total++;
                root = insertHelper(root,num);
            }
    
            public TreeNode insertHelper(TreeNode root,int num){
    
                if(root == null) return new TreeNode(num);
    
    
    
                if(root.val <= num){
    
                    root.right = insertHelper(root.right,num);
                } else {
                    root.count++;
                    root.left = insertHelper(root.left,num);
    
                }
    
                return root;
    
    
            }
        }
    
        class TreeNode{
            TreeNode left;
            TreeNode right;
            int val;
            int count;
    
            TreeNode(int val){
                this.val = val;
            }
    
        }
    
        MedianFinder(){
            tree = new Tree();
    
        }
    
        // Adds a number into the data structure.
        public void addNum(int num) {
            this.tree.insert(num);
        }
    
        // Returns the median of current data stream
        public double findMedian() {
    
    
            if(tree.total % 2 == 0){
                int a = findRank(tree.root,tree.total / 2 - 1).val;
                int b = findRank(tree.root,tree.total / 2).val;
                return (a + b) / 2.0;
    
            } else {
                return findRank(tree.root, tree.total / 2).val;
    
            }
    
    
    
    
        }
    
        public TreeNode findRank(TreeNode root, int k){
            //System.out.println(k);
            if(root == null)return null;
    
            if(root.count == k)return root;
    
            if(root.count < k){
                return findRank(root.right,k - root.count - 1);
            } else {
                return findRank(root.left,k);
            }
    
    
        }
    
        public static void main(String[] args){
            MedianFinder mf = new MedianFinder();
            mf.addNum(1);
            mf.addNum(2);
            mf.addNum(3);
            mf.addNum(4);
            mf.addNum(0);
            mf.addNum(10);
            mf.addNum(12);
            //mf.tree.display(mf.tree.root);
    
            System.out.println(mf.findMedian());
        }
    }
    
    // Your MedianFinder object will be instantiated and called as such:
    // MedianFinder mf = new MedianFinder();
    // mf.addNum(1);
    // mf.findMedian();
    

    相关文章

      网友评论

          本文标题:[295]find median from data strea

          本文链接:https://www.haomeiwen.com/subject/ulxzvttx.html