算法奇妙屋(四十四)-贪心算法学习之路11

文章目录

一. 力扣 1262. 可被三整除的最大和

1. 题目解析

2. 算法原理

主要思想是正难则反, 先求总和sum, 再根据情况讨论, 本题有贪心和动态规划两种解法, 这里只给出贪心

3. 代码

java 复制代码
class Solution {
    public int maxSumDivThree(int[] nums) {
        int sum = 0;
        for (int x : nums) {
            sum += x;
        }
        if (sum % 3 == 0) {
            return sum;
        } else if (sum % 3 == 1) {
            int min1 = 0x3f3f3f3f, min2 = 0x3f3f3f3f, min = 0x3f3f3f3f;
            for (int x : nums) {
                if (x % 3 == 1 && x < min) {
                    min = x;
                }
                if (x % 3 == 2) {
                    if (x <= min1) {
                        min2 = min1;
                        min1 = x;
                    } else if (min1 < x && x < min2) {
                        min2 = x;
                    }
                }
            }
            return Math.max(sum - min, sum - min1 - min2);
        }else {
            int min1 = 0x3f3f3f3f, min2 = 0x3f3f3f3f, min = 0x3f3f3f3f;
            for (int x : nums) {
                if (x % 3 == 2 && x < min) {
                    min = x;
                }
                if (x % 3 == 1) {
                    if (x <= min1) {
                        min2 = min1;
                        min1 = x;
                    } else if (min1 < x && x < min2) {
                        min2 = x;
                    }
                }
            }
            return Math.max(sum - min, sum - min1 - min2);
        }
    }
}

二. 力扣 1054. 距离相等的条形码

1. 题目解析

有多个相同元素的数组, 重新排列使其相邻元素不相同

2. 算法原理

这道题的算法原理很简单, 模拟一遍, 间隔填写

3. 代码

java 复制代码
class Solution {
    Map<Integer, Integer> hash;

    public int[] rearrangeBarcodes(int[] barcodes) {
        hash = new HashMap<>();
        int val = 0, count = 0;
        int n = barcodes.length;
        // 把元素与个数丢入哈希表, 同时找出最多的相同元素
        for (int x : barcodes) {
            hash.put(x, hash.getOrDefault(x, 0) + 1);
            if (count < hash.get(x)) {
                count = hash.get(x);
                val = x;
            }
        }
        int[] ret = new int[n];
        // 图中第一个位置对应的就是0号位置
        int index = 0;
        for (int i = 0; i < count; i++) {
            ret[index] = val;
            index += 2;
        }
        // 删除val
        hash.remove(val);
        // 添加其他元素, 遍历key, 再在内循环遍历出现的次数
        for (int x : hash.keySet()) {
            for (int i = 0; i < hash.get(x); i++) {
                // 当index大于数组长度时, 说明偶数位置(图中的奇数位置)已经遍历完, 这里将index从1开始, 因为元素个数和ret长度一致, 因此仅会修改一次
                if (index > n - 1) index = 1; 
                ret[index] = x;
                index += 2;
            }
        }
        return ret;
    }
}

三. 力扣 767. 重构字符串

1. 题目解析

和上道题很相似, 这里无非换成了字符, 同时要注意, 可能存在无法排列的情况

2. 算法原理

当单一字符的个数超过了(n + 1) / 2时, 无论怎么排序都无法满足题目要求

3. 代码

java 复制代码
class Solution {
    public String reorganizeString(String s) {
        char[] c = s.toCharArray();
        int n = c.length;
        // 因为这里全是小写字符, 用数组代替哈希表
        int[] hash = new int[26];
        char val = '0';
        int count = 0;
        for (char ch : c) {
            hash[ch - 'a']++;
            if (count < hash[ch - 'a']) {
                val = ch;
                count = hash[ch - 'a'];
            }
        }
        if (count > (n + 1) / 2) return "";
        char[] ret = new char[n];
        int index = 0;
        for (int i = 0; i < count; i++) {
            ret[index] = val;
            index += 2;
        }
        hash[val - 'a'] = 0;
        for (int i = 0; i < 26; i++) {
            for (int j = 0; j < hash[i]; j++) {
                if (index > n - 1) index = 1;
                ret[index] = (char)(i + 'a');
                index += 2;
            }
        }
        return new String(ret);
    }
}
相关推荐
:12127 分钟前
java基础
java·开发语言
曹牧1 小时前
Spring:@RequestMapping注解,匹配的顺序与上下文无关
java·后端·spring
空中海1 小时前
Kubernetes 入门基础与核心架构
贪心算法·架构·kubernetes
daixin88481 小时前
cursor无法正常使用gpt5.5等模型解决方案
java·redis·cursor
星幻元宇VR1 小时前
VR航空航天科普设备【VR时空直升机】
科技·学习·安全·生活·vr
_李小白2 小时前
【android opencv学习笔记】Day 2: Mat类(图片数据结构体)
android·opencv·学习
智者知已应修善业2 小时前
【51单片机按键调节占空比3位数码管显示】2023-8-24
c++·经验分享·笔记·算法·51单片机
韦禾水2 小时前
记录一次项目部署到tomcat的异常
java·tomcat
曦月合一2 小时前
树莓派安装jdk、tomcat、vnc、谷歌浏览器开机自启等环境配置
java·tomcat·树莓派
harder3213 小时前
RMP模式的创新突破
开发语言·学习·ios·swift·策略模式