Java日记2018-06-07

41.1 数据流中的中位数

后面再看
考虑将数据序列从中间开始分为两个部分,左边部分使用大根堆表示,右边部分使用小根堆存储。每遍历一个数据,计数器count增加1,当count是偶数时,将数据插入小根堆;当count是奇数时,将数据插入大根堆。当所有数据遍历插入完成后(时间复杂度为O(logn)O(logn),如果count最后为偶数,则中位数为大根堆堆顶元素和小根堆堆顶元素和的一半;如果count最后为奇数,则中位数为小根堆堆顶元素。

下午重来

public class Solution {
    // 大顶堆,存储左半边元素
    private PriorityQueue<Integer> left = new PriorityQueue<>((o1, o2) -> o2 - o1);
    // 小顶堆,存储右半边元素,并且右半边元素都大于左半边
    private PriorityQueue<Integer> right = new PriorityQueue<>();
    // 当前数据流读入的元素个数
    private int N = 0;

    public void Insert(Integer val) {
        // 插入要保证两个堆存于平衡状态
        if (N % 2 == 0) {
            // N 为偶数的情况下插入到右半边。
            // 因为右半边元素都要大于左半边,但是新插入的元素不一定比左半边元素来的大,
            // 因此需要先将元素插入左半边,然后利用左半边为大顶堆的特点,取出堆顶元素即为最大元素,此时插入右半边
            left.add(val);
            right.add(left.poll());
        } else {
            right.add(val);
            left.add(right.poll());
        }
        N++;
    }

    public Double GetMedian() {
        if (N % 2 == 0)
            return (left.peek() + right.peek()) / 2.0;
        else
            return (double) right.peek();
    }
}

41.2 字符流中第一个不重复的字符
因为一个字符不会超过8位,所以创建一个大小为256的整形数组,创建一个List,存放只出现一次的字符。insert时先对该字符所在数组位置数量+1,再判断该位置的值是否为1,如果为1,就添加到List中,不为1,则表示该字符已出现不止1次,然后从List中移除,取出时先判断List的size是否为0,不为0直接List.get(0),就可以得到结果,否则返回‘#’

方法不难想,主要是实现由坑,看注释

//41.2 字符流中第一个不重复的字符
    private static int[] chacnt = new int[256];
    private static ArrayList<Character> lst = new ArrayList<Character>();
    public static void insert(char ch){
        chacnt[ch]++;
        if(chacnt[ch]==1){
            lst.add(ch);
        }else{
            //注意這裡要強制轉換一下
            lst.remove((Character)ch);
        }
    }
    public static char findFist() {
        if (lst.size() == 0) {
            return '#';
        } else {

            return lst.get(0);
        }
    }
    
  1. 连续子数组的最大和
    判断和是否大于0,大于0继续加,小于0重新开始
//42. 连续子数组的最大和
    public static int  maxsum(int[] arr) {
        if (arr == null || arr.length == 0)
            return -1;
        int sum=0;
        int res=0;
        for(int val:arr){
            if(sum>0) {
                sum= val+sum;;
            } else{
                sum=val;
            }
            res=Math.max(sum, res);
        }
        return res;
    }
  1. 从 1 到 n 整数中 1 出现的次数
    很绕
    不直观的算法 参考 https://blog.csdn.net/yi_afly/article/details/52012593 没太理解,今天再想想
    若weight为0,则1出现次数为roundbase
    若weight为1,则1出现次数为round
    base+former+1
    若weight大于1,则1出现次数为rount*base+base
public static int count(int n) {
        if(n<1) return 0;
        int round = n;
        int base =1;
        int cnt=0;
        while(round>0) {
            int weight = round%10;
            round/=10;
            cnt+= cnt*base;
            if(weight==1)
                cnt+=(n%base)+1;
            else if(weight>1)
                cnt+=base;
            base*=10;
        }
        return cnt;
    }
©著作权归作者所有,转载或内容合作请联系作者
【社区内容提示】社区部分内容疑似由AI辅助生成,浏览时请结合常识与多方信息审慎甄别。
平台声明:文章内容(如有图片或视频亦包括在内)由作者上传并发布,文章内容仅代表作者本人观点,简书系信息发布平台,仅提供信息存储服务。

相关阅读更多精彩内容

  • Spring Cloud为开发人员提供了快速构建分布式系统中一些常见模式的工具(例如配置管理,服务发现,断路器,智...
    卡卡罗2017阅读 136,242评论 19 139
  • 临近冬日的风清爽宜人,阳光发出温和的温度。我坐在椅子上,一本化学书,一瓶咖啡,手机发出欢畅的莫扎特钢琴曲,一切让...
    象山居士阅读 1,310评论 0 0
  • ———“一起”app“美阅读书”群组四月寄语 “燕子去了,有再来的时候;杨柳枯了,有再青的时候;桃花谢了,有再开的...
    b2efeb6ea406阅读 3,931评论 0 0
  • 今早,上课的路上,小七突然拉了拉我的衣袖,冲我挤眉弄眼到“小木欧巴,你感觉前面那个妹纸怎么样?” “哪个啊?”我问...
    第五个名字阅读 2,425评论 2 3

友情链接更多精彩内容