題目
劍指 Offer 45. 把陣列排成最小的數
思路1
- 將整數陣列轉化成字串陣列
- 然後使用Arrays工具類的sort方法幫助我們排序
程式碼
class Solution {
public String minNumber(int[] nums) {
int length = nums.length;
// 將整數陣列轉化成字串陣列
String[] str = new String[length];
for (int i = 0; i < length; i++) {
str[i] = String.valueOf(nums[i]);
}
// 使用Java自帶排序
Arrays.sort(str, new Comparator<String>() {
@Override
public int compare(String o1, String o2) {
return (o1+o2).compareTo(o2+o1);
}
});
// 將字串陣列裡的按順序拼接
StringBuilder sb = new StringBuilder();
for (String s : str) {
sb.append(s);
}
return sb.toString();
}
}
複雜度分析
- 時間複雜度:\(O(NlogN)\)
- 空間複雜度:\(O(N)\)
思路2
- 自定義排序規則
- 可以使用氣泡排序比較好理解一點,也可以使用快速排序
- 排序規則是這樣的,通過拼接字串拼接xy:
- 如果
x+y > y+x
,那麼說明x
大於y
- 如果
x+y < y+x
,那麼說明x
小於y
- 按照這個排序規則,可以得出類似升序排序,升序排序是前面的數字要小於後面的數字,這個題目也是要求前面的數字在該題環境下要小於後面的數字
- 因此我們可以得出以下程式碼:
程式碼
class Solution {
public String minNumber(int[] nums) {
int length = nums.length;
// 將整數陣列轉化成字串陣列
String[] str = new String[length];
for (int i = 0; i < length; i++) {
str[i] = String.valueOf(nums[i]);
}
// 自定義排序規則的快速排序
quickSort(str, 0, length-1);
// 將字串陣列裡的按順序拼接
StringBuilder sb = new StringBuilder();
for (String s : str) {
sb.append(s);
}
return sb.toString();
}
public void quickSort(String[] arr, int left, int right) {
String pivot = arr[(left + right) / 2];
int l = left;
int r = right;
while (l <= r) {
// 因為left+pivot要滿足大於pivot+left,然後和右邊的交換,這樣子小的才能在左邊
while ((arr[l] + pivot).compareTo(pivot + arr[l]) < 0) {
l++;
}
// 因為right+pivot要滿足小於pivot+right,然後和左邊的交換,這樣子大的才能在右邊
while ((arr[r] + pivot).compareTo(pivot + arr[r]) > 0) {
r--;
}
// 這一步進行交換,就是將大的移到右邊,小的移到左邊
if (l <= r) {
String temp = arr[l];
arr[l] = arr[r];
arr[r] = temp;
l++;
r--;
}
}
// 遞迴左邊
if (r > left) {
quickSork(arr, left, r);
}
// 遞迴右邊
if (l < right) {
quickSork(arr, l, right);
}
}
}
複雜度分析
- 時間複雜度:\(O(NlogN)\)
- 空間複雜度:\(O(N)\)
思路3
- 和思路2一樣,也是使用快速排序,只是快速排序實現的方法不一樣
程式碼
class Solution {
public String minNumber(int[] nums) {
int length = nums.length;
// 將整數陣列轉化成字串陣列
String[] str = new String[length];
for (int i = 0; i < length; i++) {
str[i] = String.valueOf(nums[i]);
}
// 快速排序
quickSork(str, 0, length-1);
// 將字串陣列裡的按順序拼接
StringBuilder sb = new StringBuilder();
for (String s : str) {
sb.append(s);
}
return sb.toString();
}
public void quickSork(String[] arr, int left, int right) {
if (left < right) {
int l = left;
int r = right;
String pivot = arr[l];
while (l < r) {
// 因為升序,所以right要大於pivot
while (l < r && (arr[r] + pivot).compareTo(pivot + arr[r]) >= 0) {
r--;
}
arr[l] = arr[r];
// 因為升序,所以left要小於於pivot
while (l < r && (arr[l] + pivot).compareTo(pivot + arr[l]) <= 0) {
l++;
}
arr[r] = arr[l];
}
arr[l] = pivot;
quickSork(arr, left, l-1);
quickSork(arr, l+1, right);
}
}
}
複雜度分析
- 時間複雜度:\(O(NlogN)\)
- 空間複雜度:\(O(N)\)