把数组排成最小的数
输入一个非负整数数组,把数组里所有数字拼接起来排成一个数,打印能拼接出的所有数字中最小的一个。
示例 1:
输入: [10,2]
输出: “102”
示例 2:
输入: [3,30,34,5,9]
输出: “3033459”
这题的思路其实不难,用到自定义排序方法。定义排序方法:
s
t
r
[
a
]
+
s
t
r
[
b
]
>
s
t
r
[
b
]
+
s
t
r
[
a
]
得到
a
>
b
str[a]+str[b]>str[b]+str[a] 得到 a>b
str[a]+str[b]>str[b]+str[a]得到a>b
用这种方法将数组中的元素从小到大排序即可。
我们借用快速排序,代码如下:
class Solution:
def minNumber(self, nums: List[int]) -> str:
def quick_sprt(l: int, r: int):
if (l >= r): return
i, j = l, r
while(i < j):
while(s[j] + s[l] >= s[l] + s[j] and i < j): j = j - 1
while(s[i] + s[l] <= s[l] + s[i] and i < j): i = i + 1
s[i], s[j] = s[j], s[i]
s[i], s[l] = s[l], s[i]
quick_sprt(l, i - 1)
quick_sprt(i + 1, r)
s = [str(num) for num in nums]
quick_sprt(0, len(s) - 1)
return ''.join(s)
这个快排的代码和上一次的贴的代码有点不一样,更加的简洁,其实思想也很好理解,每次确定
s
[
l
]
s[l]
s[l]的位置,三个while循环的结果就是让数组呈现出这种效果:
此处注意几个要点:
1.while循环还有
i
<
j
i< j
i<j的限制。可以脑补一下假如数组是[1,2,3,4]数组一路顺滑,然后j疯狂减,超出索引。
2.判断条件带等于号,是因为如果能开启左循环,就要跳过l本身。那你可能会想,初始条件设置成i = l + 1不就行了吗?但是假如数组是[1,2,3,4],1本来就应该停在第一个位置,这也是我们先遍历右循环再遍历左循环的原因。