2021-11-24:把一个01字符串切成多个部分,要求每一部分的0和1比例一样,同时要求尽可能多的划分, 比如 : 01010101, 01 01 01 01 这是一种切法,0和1比例为 1 : 1
2021-11-24:把一个01字符串切成多个部分,要求每一部分的0和1比例一样,同时要求尽可能多的划分,
比如 : 01010101,
01 01 01 01 这是一种切法,0和1比例为 1 : 1,
0101 0101 也是一种切法,0和1比例为 1 : 1,
两种切法都符合要求,但是那么尽可能多的划分为第一种切法,部分数为4,
比如 : 00001111,
只有一种切法就是00001111整体作为一块,那么尽可能多的划分,部分数为1,
给定一个01字符串str,假设长度为N,要求返回一个长度为N的数组ans,
其中ans[i] = str[0…i]这个前缀串,要求每一部分的0和1比例一样,同时要求尽可能多的划分下,部分数是多少?
输入: str = “010100001”,
输出: ans = [1, 1, 1, 2, 1, 2, 1, 1, 3]。
来自京东。
答案2021-11-24:
考点是分数表示,保证没有精度损失。
1.分数表示。
分子是0的个数,分母是1的个数。
key是分子/分母。在go语言中,用结构体表示分数。
value是个数。
2.如果整体的分数和局部的分数一样,那么整体的个数一定加1。
时间复杂度:O((N)。
空间复杂度:O(N)。
代码用golang编写。代码如下:
package main
import "fmt"
func main() {
arr := []int{0, 0, 1, 0, 1, 0, 0, 1, 0, 1, 0, 0}
ret := split(arr)
fmt.Println("两个变量表示分数:", ret)
ret = split2(arr)
fmt.Println("结构体表示分数:", ret)
}
type r struct {
a int
b int
}
func NewR(a int, b int) r {
res := r{}
g := gcd(a, b)
res.a = a / g
res.b = b / g
return res
}
func split2(arr []int) []int {
// key : 分子
// value : 属于key的分母表, 每一个分母,及其 分子/分母 这个比例,多少个前缀拥有
pre := make(map[r]int)
n := len(arr)
ans := make([]int, n)
zero := 0 // 0出现的次数
one := 0 // 1出现的次数
for i := 0; i < n; i++ {
if arr[i] == 0 {
zero++
} else {
one++
}
if zero == 0 || one == 0 {
ans[i] = i + 1
} else { // 0和1,都有数量 -> 最简分数
pre[NewR(zero, one)]++
ans[i] = pre[NewR(zero, one)]
}
}
return ans
}
// 001010010100...
func split(arr []int) []int {
// key : 分子
// value : 属于key的分母表, 每一个分母,及其 分子/分母 这个比例,多少个前缀拥有
//HashMap<Integer, HashMap<Integer, Integer>> pre = new HashMap<>();
pre := make(map[int]map[int]int)
n := len(arr)
ans := make([]int, n)
zero := 0 // 0出现的次数
one := 0 // 1出现的次数
for i := 0; i < n; i++ {
if arr[i] == 0 {
zero++
} else {
one++
}
if zero == 0 || one == 0 {
ans[i] = i + 1
} else { // 0和1,都有数量 -> 最简分数
gcd := gcd(zero, one)
a := zero / gcd
b := one / gcd
// a / b 比例,之前有多少前缀拥有? 3+1 4 5+1 6
if _, ok := pre[a]; !ok {
pre[a] = make(map[int]int)
}
if _, ok := pre[a][b]; !ok {
pre[a][b] = 1
} else {
pre[a][b] = pre[a][b] + 1
}
ans[i] = pre[a][b]
}
}
return ans
}
func gcd(m, n int) int {
if n == 0 {
return m
} else {
return gcd(n, m%n)
}
}
执行结果如下:
公众号:福大大架构师每日一题
【推荐】国内首个AI IDE,深度理解中文开发场景,立即下载体验Trae
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步
· winform 绘制太阳,地球,月球 运作规律
· TypeScript + Deepseek 打造卜卦网站:技术与玄学的结合
· AI 智能体引爆开源社区「GitHub 热点速览」
· Manus的开源复刻OpenManus初探
· 写一个简单的SQL生成工具
2020-11-24 2020-11-24:n个物品每个物品都有一定价值,分给2个人,怎么分两个人的价值差最小?