Given two arrays of length m and n with digits 0-9 representing two numbers. Create the maximum number of length k <= m + n from digits of the two. The relative order of the digits from the same array must be preserved. Return an array of the k digits. You should try to optimize your time and space complexity.
classSolution { public: vector<int> maxNumber(vector<int>& nums1, vector<int>& nums2, int k){ vector<int> ans(k, 0); for (int i = max(0, k - (int)nums2.size()); i <= min(k, (int)nums1.size()); i++) { vector<int> res1 = get_max_sub_array(nums1, i); vector<int> res2 = get_max_sub_array(nums2, k - i); vector<int> res(k, 0); int pos1 = 0, pos2 = 0, tpos = 0; while (pos1 < res1.size() || pos2 < res2.size()) { res[tpos++] = greater(res1, pos1, res2, pos2) ? res1[pos1++] : res2[pos2++]; } if (!greater(ans, 0, res, 0)) ans = res; } return ans; }
boolgreater(const vector<int> & a, int start1, const vector<int> &b, int start2){ for (; start1 < a.size() && start2 < b.size(); start1++, start2++) { if (a[start1] > b[start2]) returntrue; if (a[start1] < b[start2]) returnfalse; } return start1 != a.size(); }
vector<int> get_max_sub_array(const vector<int> &nums, constint& k){ vector<int> res(k,0); int len = 0 , n = nums.size(); for (int i = 0; i < n; i++) { while (len && len + n - i > k && nums[i] > res[len - 1]) len--; if (len < k) res[len++] = nums[i]; } return res; } };
defget_max_sub_array(nums, k): res , n = [] ,len(nums) for i in xrange(n): while res andlen(res) + n - i > k and nums[i] > res[-1]: res.pop() iflen(res) < k: res.append(nums[i]) return res
ans = [0] * k for i in xrange(max(0, k - len(nums2)), min(k, len(nums1)) + 1): res1 = get_max_sub_array(nums1, i) res2 = get_max_sub_array(nums2, k - i) ans = max(ans, [max(res1, res2).pop(0) for _ in xrange(k)]) return ans
/** * Created by hrwhisper on 2015/11/23. * https://www.hrwhisper.me/leetcode-create-maximum-number/ */
publicclassSolution { publicint[] maxNumber(int[] nums1, int[] nums2, int k) { intget_from_nums1= Math.min(nums1.length, k); int[] ans = newint[k]; for (inti= Math.max(k - nums2.length, 0); i <= get_from_nums1; i++) { int[] res1 = newint[i]; if (i > 0) res1 = solve(nums1, i); int[] res2 = newint[k - i]; if (k - i > 0) res2 = solve(nums2, k - i); intpos1=0, pos2 = 0, tpos = 0; int[] res = newint[k]; while (res1.length > 0 && res2.length > 0 && pos1 < res1.length && pos2 < res2.length) { if (res1[pos1] > res2[pos2]) res[tpos++] = res1[pos1++]; elseif (res1[pos1] < res2[pos2]) res[tpos++] = res2[pos2++]; else { intx= pos1; inty= pos2; while (x < res1.length && y < res2.length && res1[x] == res2[y]) { x++; y++; } if (x < res1.length && y < res2.length) { if (res1[x] < res2[y]) { res[tpos++] = res2[pos2++]; } else { res[tpos++] = res1[pos1++]; } } elseif (x < res1.length) { res[tpos++] = res1[pos1++]; } else { res[tpos++] = res2[pos2++]; } } } while (pos1 < res1.length) res[tpos++] = res1[pos1++]; while (pos2 < res2.length) res[tpos++] = res2[pos2++];
if (updateAns(ans, res)) ans = res; } return ans; }
publicbooleanupdateAns(int[] ans, int[] res) { for (inti=0; i < ans.length; i++) { if (ans[i] > res[i]) returnfalse; if (ans[i] < res[i]) returntrue; } returnfalse; }
publicint[] solve(int[] nums, int k) { int[] res = newint[k]; intlen=0; for (inti=0; i < nums.length; i++) { while (len > 0 && len + nums.length - i > k && res[len - 1] < nums[i]) { len--; } if (len < k) res[len++] = nums[i]; } return res; } }