Given a positive integer num
, split it into two non-negative integers num1
and num2
such that:
- The concatenation of
num1
andnum2
is a permutation ofnum
.- In other words, the sum of the number of occurrences of each digit in
num1
andnum2
is equal to the number of occurrences of that digit innum
.
- In other words, the sum of the number of occurrences of each digit in
num1
andnum2
can contain leading zeros.
Return the minimum possible sum of num1
and num2
.
Notes:
- It is guaranteed that
num
does not contain any leading zeros. - The order of occurrence of the digits in
num1
andnum2
may differ from the order of occurrence ofnum
.
Example 1:
Input: num = 4325 Output: 59 Explanation: We can split 4325 so thatnum1
is 24 and num2is
35, giving a sum of 59. We can prove that 59 is indeed the minimal possible sum.
Example 2:
Input: num = 687 Output: 75 Explanation: We can split 687 so thatnum1
is 68 andnum2
is 7, which would give an optimal sum of 75.
Constraints:
10 <= num <= 109
Approach 1: Count + Greedy
We first use a hash table or array cnt
to count the number of times each digit appears in num
, and use the variable n
to record the number of digits in num
.
Then, enumerate the number of digits nums
, and assign the numbers in cnt
in ascending order alternately to num1
and num2
, and record it in an array of length $ans
. Finally, return the sum of the two numbers in ans
.
The time complexity is num
; and num
, which is
Approach 2: Sorting + Greedy
We can convert num
to a string or character array and sort it. Then assign the numbers in the sorted array in ascending order alternately to num1
and num2
, and finally return the sum of num1
and num2
.
The time complexity is num
.
class Solution:
def splitNum(self, num: int) -> int:
cnt = Counter()
n = 0
while num:
cnt[num % 10] += 1
num //= 10
n += 1
ans = [0] * 2
j = 0
for i in range(n):
while cnt[j] == 0:
j += 1
cnt[j] -= 1
ans[i & 1] = ans[i & 1] * 10 + j
return sum(ans)
class Solution:
def splitNum(self, num: int) -> int:
s = sorted(str(num))
return int(''.join(s[::2])) + int(''.join(s[1::2]))
class Solution {
public int splitNum(int num) {
int[] cnt = new int[10];
int n = 0;
for (; num > 0; num /= 10) {
++cnt[num % 10];
++n;
}
int[] ans = new int[2];
for (int i = 0, j = 0; i < n; ++i) {
while (cnt[j] == 0) {
++j;
}
--cnt[j];
ans[i & 1] = ans[i & 1] * 10 + j;
}
return ans[0] + ans[1];
}
}
class Solution {
public int splitNum(int num) {
char[] s = (num + "").toCharArray();
Arrays.sort(s);
int[] ans = new int[2];
for (int i = 0; i < s.length; ++i) {
ans[i & 1] = ans[i & 1] * 10 + s[i] - '0';
}
return ans[0] + ans[1];
}
}
class Solution {
public:
int splitNum(int num) {
int cnt[10]{};
int n = 0;
for (; num; num /= 10) {
++cnt[num % 10];
++n;
}
int ans[2]{};
for (int i = 0, j = 0; i < n; ++i) {
while (cnt[j] == 0) {
++j;
}
--cnt[j];
ans[i & 1] = ans[i & 1] * 10 + j;
}
return ans[0] + ans[1];
}
};
class Solution {
public:
int splitNum(int num) {
string s = to_string(num);
sort(s.begin(), s.end());
int ans[2]{};
for (int i = 0; i < s.size(); ++i) {
ans[i & 1] = ans[i & 1] * 10 + s[i] - '0';
}
return ans[0] + ans[1];
}
};
func splitNum(num int) int {
cnt := [10]int{}
n := 0
for ; num > 0; num /= 10 {
cnt[num%10]++
n++
}
ans := [2]int{}
for i, j := 0, 0; i < n; i++ {
for cnt[j] == 0 {
j++
}
cnt[j]--
ans[i&1] = ans[i&1]*10 + j
}
return ans[0] + ans[1]
}
func splitNum(num int) int {
s := []byte(strconv.Itoa(num))
sort.Slice(s, func(i, j int) bool { return s[i] < s[j] })
ans := [2]int{}
for i, c := range s {
ans[i&1] = ans[i&1]*10 + int(c-'0')
}
return ans[0] + ans[1]
}
function splitNum(num: number): number {
const cnt = new Array(10).fill(0);
let n = 0;
for (; num > 0; num = Math.floor(num / 10)) {
++cnt[num % 10];
++n;
}
const ans = new Array(2).fill(0);
for (let i = 0, j = 0; i < n; ++i) {
while (cnt[j] === 0) {
++j;
}
--cnt[j];
ans[i & 1] = ans[i & 1] * 10 + j;
}
return ans[0] + ans[1];
}
function splitNum(num: number): number {
const s: string[] = String(num).split('');
s.sort();
const ans: number[] = new Array(2).fill(0);
for (let i = 0; i < s.length; ++i) {
ans[i & 1] = ans[i & 1] * 10 + Number(s[i]);
}
return ans[0] + ans[1];
}