2022-08-28 周赛总结

6160. 和有限的最长子序列
解法:排序+前缀和+二分
做的时候没有想到可以排序,最后选择大顶堆去做的:

class Solution {
    public int[] answerQueries(int[] nums, int[] queries) {
        int[] ans = new int[queries.length];
        for (int i = 0; i < queries.length; i++) {
            ans[i] = maxLength(nums,queries[i]);
        }
        return ans;
    }
    
    public int maxLength(int[] nums, int t) {
        PriorityQueue<Integer> heap = new PriorityQueue<>((a,b)->(b-a));
        int sum = 0;
        for (int num : nums) {
            if (num > t) {
                continue;
            }
            if (num + sum <= t) {
                heap.offer(num);
                sum += num;
            } else if (num < heap.peek()) {
                sum -= heap.peek();
                heap.poll();
                heap.offer(num);
                sum += num;
            }
        }
        return heap.size();
    }
}

6161. 从字符串中移除星号
解题思路:栈 每当当前元素是时,就把栈顶的元素弹出,最终栈中剩下的元素就是结果。
我自己在做的时候选择从后面像前面遍历,剔除掉
,最终生成目标字符串。

class Solution {
    public String removeStars(String s) {
        StringBuffer sb = new StringBuffer();
        char[] ch = s.toCharArray();
        int i = ch.length - 1;
        int times = 0;
        while (i >= 0) {
            while (i >= 0 && ch[i] != '*') {
                sb.append(ch[i--]);
            }
            while (i >= 0 && ch[i] == '*') {
                times++;
                i--;
            }
            while (i >= 0 && ch[i] != '*' && times > 0) {
                times--;
                i--;
            }
        }
        return sb.reverse().toString();
    }
}

6162. 收集垃圾的最少总时间
解题思路:
垃圾回收时间分为两部分:

  1. 收垃圾的时间
  2. 垃圾车走到对应垃圾最后一站所需要的时间
    对于第一种情况,就是整个garbage所有字符串的长度的和,第二种情况需要计算出每种垃圾一直到那一站才结束。
class Solution {
    public int garbageCollection(String[] garbage, int[] travel) {
        int ans = 0;
        int g = 0, p = 0, m = 0, sum = 0, i = 1;
        for (String str : garbage) {
            ans += str.length();
            if (str.indexOf('G') >= 0) {
                g = sum;
            }
            if (str.indexOf('P') >= 0) {
                p= sum;
            }
            if (str.indexOf('M') >= 0) {
                m = sum;
            }
            sum += i <= travel.length ? travel[i-1] : 0;
            i++;
        }
        ans += p+g+m;
        return ans;
    }
}

2392. 给定条件下构造矩阵

分析

拓扑排序
邻接表(一个节点的后继有哪些)
入读数组(记录一个节点的入度是多少)
队列(按照入度为0的节点加入队列)
得到k个数字的先后顺序, 如果依赖关系中存在环,则最终的list的个数小于k,
因为环上节点的入度永远也不会为0.

构建出行,列的先后顺序,然后平凑出完整的二维数组。
新建一个数组,用来标记行(或者列)对应的下标,即用数值得到对应的位置。

class Solution {
    public int[][] buildMatrix(int k, int[][] rowConditions, int[][] colConditions) {
        int[] row = topology(k,rowConditions);
        int[] col = topology(k,colConditions);
        if (row.length < k || col.length < k) {
            return new int[][]{};
        }
        int[][] ans = new int[k][k];
        int[] pos = new int[k];
        for (int i = 0; i < k; i++) {
            pos[row[i]] = i;
        }
        for (int i = 0; i < k; ++i) {
            ans[pos[col[i]]][i] = col[i] + 1;
        }
        return ans;
    }

    public int[] topology(int k, int[][] egdes) {
        List<Integer>[] adjoin = new ArrayList[k];
        Arrays.setAll(adjoin,e->new ArrayList<>());
        int[] times = new int[k];
        for (int[] arr : egdes) {
            int a = arr[0] - 1;
            int b = arr[1] - 1;
            times[b]++;
            adjoin[a].add(b);
        }
        Queue<Integer> queue = new LinkedList<>();
        for (int i = 0; i < k; i++) {
            if (times[i] == 0) {
                queue.offer(i);
            }
        }
        List<Integer> list = new ArrayList<>();
        while (!queue.isEmpty()) {
            int num = queue.poll();
            list.add(num);
            for (int next : adjoin[num]) {
                times[next]--;
                if (times[next] == 0) {
                    queue.offer(next);
                }
            }
        }
        int[] topology = new int[list.size()];
        for (int i = 0; i < list.size(); i++) {
            topology[i] = list.get(i);
        }
        return topology;
    }
}
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值