Loading [MathJax]/jax/output/CommonHTML/config.js
前往小程序,Get更优阅读体验!
立即前往
首页
学习
活动
专区
圈层
工具
发布
首页
学习
活动
专区
圈层
工具
MCP广场
社区首页 >专栏 >2022-01-18:将数组分成两个数组并最小化数组和的差。 给

2022-01-18:将数组分成两个数组并最小化数组和的差。 给

原创
作者头像
福大大架构师每日一题
发布于 2022-01-18 14:24:25
发布于 2022-01-18 14:24:25
6990
举报

2022-01-18:将数组分成两个数组并最小化数组和的差。

给你一个长度为 2 * n 的整数数组。你需要将 nums 分成 两个 长度为 n 的数组,分别求出两个数组的和,并 最小化 两个数组和之 差的绝对值 。nums 中每个元素都需要放入两个数组之一。

请你返回 最小 的数组和之差。

输入:nums = 3,9,7,3。

输出:2。

解释:最优分组方案是分成 3,9 和 7,3 。

数组和之差的绝对值为 abs((3 + 9) - (7 + 3)) = 2 。

力扣2035。

答案2022-01-18:

分治法。

arr -> 8 0 1 2 3 4 5 6 7

process(arr, 0, 4) [0,4)

process(arr, 4, 8) [4,8)

arr -> 8 0 1 2 3 4 5 6 7

process(arr, 0, 4) [0,4)

process(arr, 4, 8) [4,8)

arrindex....end-1这个范围上,去做选择

pick挑了几个数!

sum挑的这些数,累加和是多少!

map记录结果

HashMap<Integer, TreeSet<Integer>> map

key -> 挑了几个数,比如挑了3个数,但是形成累加和可能多个!

value -> 有序表,都记下来!

整个过程,纯暴力!2^15 -> 3万多,纯暴力跑完,依然很快!

代码用golang编写。代码如下:

代码语言:go
AI代码解释
复制
package main

import (
    "fmt"
    "math"
    "sort"
)

func main() {
    ret := minimumDifference([]int{3, 9, 7, 3})
    fmt.Println(ret)
}

func minimumDifference(arr []int) int {
    size := len(arr)
    half := size >> 1
    //HashMap<Integer, TreeSet<Integer>> lmap = new HashMap<>();
    lmap := make(map[int]map[int]struct{})
    process(arr, 0, half, 0, 0, lmap)
    //HashMap<Integer, TreeSet<Integer>> rmap = new HashMap<>();
    rmap := make(map[int]map[int]struct{})
    process(arr, half, size, 0, 0, rmap)
    sum := 0
    for _, num := range arr {
        sum += num
    }
    ans := math.MaxInt64
    for leftNum, _ := range lmap {
        for leftSum, _ := range lmap[leftNum] {
            rr := rmap[half-leftNum]
            //模拟treeset
            rarr := make([]int, 0)
            for r, _ := range rr {
                rarr = append(rarr, r)
            }
            sort.Ints(rarr)
            ri := NearestIndex2(rarr, (sum>>1)-leftSum)
            rightSum := 0
            if ri != -1 {
                rightSum = rarr[ri]
                pickSum := leftSum + rightSum
                restSum := sum - pickSum
                //ans = Math.min(ans, restSum - pickSum);
                if ans > restSum-pickSum {
                    ans = restSum - pickSum
                }
            }
        }
    }
    return ans
}

// arr -> 8   0 1 2 3      4 5 6 7
// process(arr, 0, 4)  [0,4)
// process(arr, 4, 8)  [4,8)
// arr[index....end-1]这个范围上,去做选择
// pick挑了几个数!
// sum挑的这些数,累加和是多少!
// map记录结果
// HashMap<Integer, TreeSet<Integer>> map
// key -> 挑了几个数,比如挑了3个数,但是形成累加和可能多个!
// value -> 有序表,都记下来!
// 整个过程,纯暴力!2^15 -> 3万多,纯暴力跑完,依然很快!
func process(arr []int, index int, end int, pick int, sum int, map0 map[int]map[int]struct{}) {
    if index == end {
        if _, ok := map0[pick]; !ok {
            map0[pick] = make(map[int]struct{})
        }
        map0[pick][sum] = struct{}{}
    } else {
        process(arr, index+1, end, pick, sum, map0)
        process(arr, index+1, end, pick+1, sum+arr[index], map0)
    }
}

// 在arr上,找满足<=value的最右位置
func NearestIndex2(arr []int, v int) int {
    L := 0
    R := len(arr) - 1
    index := -1 // 记录最右的对号
    for L <= R {
        mid := L + (R-L)>>1
        if arr[mid] <= v {
            index = mid
            L = mid + 1
        } else {
            R = mid - 1
        }
    }
    return index
}

执行结果如下:

图片
图片

左神java代码

moonfdd

原创声明:本文系作者授权腾讯云开发者社区发表,未经许可,不得转载。

如有侵权,请联系 cloudcommunity@tencent.com 删除。

原创声明:本文系作者授权腾讯云开发者社区发表,未经许可,不得转载。

如有侵权,请联系 cloudcommunity@tencent.com 删除。

评论
登录后参与评论
暂无评论
推荐阅读
编辑精选文章
换一批
2022-01-18:将数组分成两个数组并最小化数组和的差。
给你一个长度为 2 * n 的整数数组。你需要将 nums 分成 两个 长度为 n 的数组,分别求出两个数组的和,并 最小化 两个数组和之 差的绝对值 。nums 中每个元素都需要放入两个数组之一。
福大大架构师每日一题
2022/03/04
9080
2022-01-18:将数组分成两个数组并最小化数组和的差。
2021-08-09:给定一个有正、有负、有0的数组arr
2021-08-09:给定一个有正、有负、有0的数组arr,给定一个整数k,返回arr的子集是否能累加出k。1)正常怎么做?2)如果arr中的数值很大,但是arr的长度不大,怎么做?
福大大架构师每日一题
2021/08/09
3290
2021-08-09:给定一个有正、有负、有0的数组arr
2022-01-20: 矩形区域不超过 K 的最大数值和。 给你一个 m
给你一个 m x n 的矩阵 matrix 和一个整数 k ,找出并返回矩阵内部矩形区域的不超过 k 的最大数值和。
福大大架构师每日一题
2022/01/20
2480
2021-07-10:请返回arr中,求子数组的累加和,是<=K
2021-07-10:请返回arr中,求子数组的累加和,是<=K的并且是最大的。返回这个最大的累加和。
福大大架构师每日一题
2021/07/10
4120
2021-07-10:请返回arr中,求子数组的累加和,是<=K
LeetCode 2035. 将数组分成两个数组并最小化数组和的差(状态压缩DP)
给你一个长度为 2 * n 的整数数组。 你需要将 nums 分成 两个 长度为 n 的数组,分别求出两个数组的和,并 最小化 两个数组和之 差的绝对值 。 nums 中每个元素都需要放入两个数组之一。
Michael阿明
2022/01/07
2.5K0
LeetCode通关:数组十七连,真是不简单
数组基本上是我们最熟悉的数据结构了,刚会写“Hello World”不久,接着就是“杨辉三角”之类的练习。
三分恶
2021/08/10
4010
搞定大厂算法面试之leetcode精讲10.递归&分治
分治会将大问题拆解成小问题,拆解到最小问题之后,开始不断合并结果,递归是分治实现的一种形式或者是分治实现的一部分,分治包括三分部分,分解、计算、合并。分治的场景很多,例如快速排序,归并排序。
全栈潇晨
2021/11/29
4330
2023-03-18:给定一个长度n的数组,每次可以选择一个数x,让这个数组中所有的x都变成x+1,问你最少的操作次数,使得这个
本题可以用多种算法来解决,下面我们将介绍四种常见的做法,分别是暴力枚举、动态规划、单调栈和差分。
福大大架构师每日一题
2023/06/08
7990
2023-03-18:给定一个长度n的数组,每次可以选择一个数x,让这个数组中所有的x都变成x+1,问你最少的操作次数,使得这个
350. 两个数组的交集 II
给定两个数组,编写一个函数来计算它们的交集。 示例 1: 输入:nums1 = [1,2,2,1], nums2 = [2,2] 输出:[2,2] 示例 2: 输入:nums1 = [
编程张无忌
2021/06/10
2590
350. 两个数组的交集 II
2023-07-04:给定一个数组A, 把它分成两个数组B和C 对于数组A每个i位置的数来说, A[i] = B[i] + C[
1.定义一个递归函数 process1,接受一个数组 arr,一个索引 i,前一个增加值 preIncrease 和前一个减少值 preDecrease。
福大大架构师每日一题
2023/07/25
3210
2023-07-04:给定一个数组A, 把它分成两个数组B和C 对于数组A每个i位置的数来说, A[i] = B[i] + C[
数组刷题<下>套路分析
一、双索引技术-对撞指针1.167. 两数之和 II - 输入有序数组2. 345. 反转字符串中的元音字母3.344. 反转字符串4.125. 验证回文串5.11. 盛最多水的容器二、双索引技术-滑动窗口1.209. 长度最小的子数组2.438. 找到字符串中所有字母异位词3.76. 最小覆盖子串
公众号guangcity
2019/09/20
6070
数组刷题<下>套路分析
LeetCode 350: 两个数组的交集 II Intersection of Two Arrays II
Given two arrays, write a function to compute their intersection.
爱写bug
2019/10/30
4580
代码随想录day01--数组
给定一个整数数组 nums 和一个目标值 target,请你在该数组中找出和为目标值的那 两个 整数,并返回他们的数组下标。
ma布
2024/12/25
540
代码随想录day01--数组
2023-03-02:给定一个数组arr,长度为n, 任意相邻的两个数里面至少要有一个被选出来,组成子序列,才是合法的! 求所有可能的合法子序列中,最大中位数是
2023-03-02:给定一个数组arr,长度为n,任意相邻的两个数里面至少要有一个被选出来,组成子序列,才是合法的!求所有可能的合法子序列中,最大中位数是多少?中位数的定义为上中位数,1, 2, 3, 4的上中位数是2,1, 2, 3, 4, 5的上中位数是3,2 <= n <= 10^5,1 <= arri <= 10^9。来自京东。实习岗位笔试题。答案2023-03-02:这道题看起来是实习题,实际上有难度。方法一:要i还是不要i,递归或者动态规划。方法二:以结果为导向,二分法。时间复杂度:O(N*
福大大架构师每日一题
2023/03/02
5540
2023-03-02:给定一个数组arr,长度为n, 任意相邻的两个数里面至少要有一个被选出来,组成子序列,才是合法的! 求所有可能的合法子序列中,最大中位数是
2023-12-20:用go语言,给定一个数组arr,长度为n,在其中要选两个不相交的子数组。 两个子数组的累加和都要是T,返回
2023-12-20:用go语言,给定一个数组arr,长度为n,在其中要选两个不相交的子数组。
福大大架构师每日一题
2023/12/21
2370
2023-12-20:用go语言,给定一个数组arr,长度为n,在其中要选两个不相交的子数组。 两个子数组的累加和都要是T,返回
2023-07-17:给定一个数组arr,长度为n, 再给定一个数字k,表示一定要将arr划分成k个集合, 每个数字只能进一个集
1.定义一个结构体Info,包含两个字段:sum表示集合内所有元素的和,cnt表示集合内元素的个数。
福大大架构师每日一题
2023/07/25
2520
2023-07-17:给定一个数组arr,长度为n, 再给定一个数字k,表示一定要将arr划分成k个集合, 每个数字只能进一个集
阶段01Java基础day18集合框架04
声明:本文为原创,作者为 对弈,转载时请保留本声明及附带文章链接:http://www.duiyi.xyz/c%e5%ae%9e%e7%8e%b0%e9%9b%b7%e9%9c%86%e6%88%98%e6%9c%ba-25/
对弈
2019/09/04
5510
2023-08-30:用go语言编写。两个魔法卷轴问题。 给定一个数组arr,其中可能有正、负、0, 一个魔法卷轴可以把arr中
5.调用函数mustOneScroll(arr, 0, n-1),返回一个整数,并赋值给变量p2。
福大大架构师每日一题
2023/09/01
1970
2023-08-30:用go语言编写。两个魔法卷轴问题。 给定一个数组arr,其中可能有正、负、0, 一个魔法卷轴可以把arr中
2021-05-08:给定两个非负数组x和hp,长度都是N,再给定一个正数range
2021-05-08:给定两个非负数组x和hp,长度都是N,再给定一个正数range。x有序,xi表示i号怪兽在x轴上的位置;hpi表示i号怪兽的血量 。range表示法师如果站在x位置,用AOE技能打到的范围是: x-range,x+range,被打到的每只怪兽损失1点血量 。返回要把所有怪兽血量清空,至少需要释放多少次AOE技能?
福大大架构师每日一题
2021/05/10
5040
2021-05-08:给定两个非负数组x和hp,长度都是N,再给定一个正数range
2021-04-04:给定一个非负数组arr,和一个正数m的最大值。
2021-04-04:给定一个非负数组arr,和一个正数m。 返回arr的所有子序列中累加和%m之后的最大值。
福大大架构师每日一题
2021/04/04
8780
2021-04-04:给定一个非负数组arr,和一个正数m的最大值。
推荐阅读
2022-01-18:将数组分成两个数组并最小化数组和的差。
9080
2021-08-09:给定一个有正、有负、有0的数组arr
3290
2022-01-20: 矩形区域不超过 K 的最大数值和。 给你一个 m
2480
2021-07-10:请返回arr中,求子数组的累加和,是<=K
4120
LeetCode 2035. 将数组分成两个数组并最小化数组和的差(状态压缩DP)
2.5K0
LeetCode通关:数组十七连,真是不简单
4010
搞定大厂算法面试之leetcode精讲10.递归&分治
4330
2023-03-18:给定一个长度n的数组,每次可以选择一个数x,让这个数组中所有的x都变成x+1,问你最少的操作次数,使得这个
7990
350. 两个数组的交集 II
2590
2023-07-04:给定一个数组A, 把它分成两个数组B和C 对于数组A每个i位置的数来说, A[i] = B[i] + C[
3210
数组刷题<下>套路分析
6070
LeetCode 350: 两个数组的交集 II Intersection of Two Arrays II
4580
代码随想录day01--数组
540
2023-03-02:给定一个数组arr,长度为n, 任意相邻的两个数里面至少要有一个被选出来,组成子序列,才是合法的! 求所有可能的合法子序列中,最大中位数是
5540
2023-12-20:用go语言,给定一个数组arr,长度为n,在其中要选两个不相交的子数组。 两个子数组的累加和都要是T,返回
2370
2023-07-17:给定一个数组arr,长度为n, 再给定一个数字k,表示一定要将arr划分成k个集合, 每个数字只能进一个集
2520
阶段01Java基础day18集合框架04
5510
2023-08-30:用go语言编写。两个魔法卷轴问题。 给定一个数组arr,其中可能有正、负、0, 一个魔法卷轴可以把arr中
1970
2021-05-08:给定两个非负数组x和hp,长度都是N,再给定一个正数range
5040
2021-04-04:给定一个非负数组arr,和一个正数m的最大值。
8780
相关推荐
2022-01-18:将数组分成两个数组并最小化数组和的差。
更多 >
领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档