321. Create Maximum Number

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.

Note: You should try to optimize your time and space complexity.

Example 1:

Input:
nums1 = [3, 4, 6, 5]
nums2 = [9, 1, 2, 5, 8, 3]
k = 5
Output:
[9, 8, 6, 5, 3]

Example 2:

Input:
nums1 = [6, 7]
nums2 = [6, 0, 4]
k = 5
Output:
[6, 7, 6, 0, 4]

Example 3:

Input:
nums1 = [3, 9]
nums2 = [8, 9]
k = 3
Output:
[9, 8, 9]

There may be some excellent solutions, but I just think of a sample solution using greedy and pass through.
We need to get a number with k’s length from two vectors, then we have the following situations:
gain 0 number from nums1, k numbers from nums2;
gain 1 number from nums1, k - 1 numbers from nums2;

gain k numbers from nums1, 0 number from nums2.
And we should consider the size of vector to judge whether we can get enough numbers from it.
For gettting maximum number, each number we extract from nums1 and nums2 should be the maximum too, that’s what the function maxVector does, then we merge the two number from nums1 and nums2 into one number while make sure the consequence number is biggest. We compare among all the possible combinations, choose the biggest one, and that’ what we want.

class Solution {
public:
    bool greaterVector(vector<int>& nums1, int nums1_start, vector<int>& nums2, int nums2_start)
    {
        //We compare nums1(nums1.begin() + nums1_start, nums1.end()) with nums2(nums2.begin() + nums2_start, nums2.end()).
        //The way to compare two vector is exactly same as the way to compare two strings.
        //If nums1[nums1_start] == nums2[nums2_start], then compare the next elememts of nums1 and nums2.
        while (nums1_start < nums1.size() && nums2_start < nums2.size() && nums1[nums1_start] == nums2[nums2_start]) { nums1_start++; nums2_start++; };
        //The reason that jumping the while code segment belongs to the set:
        //-- nums1_start == nums1.size()
        //-- nums2_start == nums2.size()
        //nums1[nums1_start] != nums2[nums2_start]
        return (nums2_start == nums2.size() || (nums1_start < nums1.size() && nums1[nums1_start] > nums2[nums2_start]));
    }
    vector<int> maxVector(vector<int>& nums, int k)
    {
        if (k == 0)return {};
        //The variable result is the vector for result.
        vector<int> result(k, INT_MIN);
        //We should go through the nums for get the result. In order to ensure the result right, we should fill it as the following way.
        //Let us suppose we haven't gone through the nums, and we are on the index i currently, and we have fill j numbers into the result.
        //Apparently, the number of the elements we have passed is nums.size() - i, and if (nums.size() - i) <= (k - j), then we have no choice but fill the result by the other elements which have a bigger index greater than i.
        //In the situation we have enough choices, if nums[i] > result[j - 1], the we substitute result[j - 1] with nums[i], it's because we will get a bigger vector by doing that.
        int j = 0;
        for (int i = 0; i < nums.size(); i++)
        {
            while ((nums.size()) - i >(k - j) && j > 0 && nums[i] > result[j - 1])j--;
            if (j < k)result[j++] = nums[i];
        }
        return result;
    }
    vector<int> mergeVector(vector<int>& nums1, vector<int>& nums2)
    {
        int i = 0, j = 0, k = 0;
        vector<int> result(nums1.size() + nums2.size(), 0);
        while (i < nums1.size() && j < nums2.size())
        {
            if (nums1[i] > nums2[j]) { result[k++] = nums1[i++]; }
            else if (nums1[i] < nums2[j]) { result[k++] = nums2[j++]; }
            else
            {
                //Let us consider the situation if nums1[i] == nums2[j], we choose the first letter of the bigger vector between nums1(nums1.begin() + i, nums1.end()) and nums2(nums2.begin() + j, nums2.end())
                //For example, the left parts of nums1 and nums2 are "06132" and "05322", which should we choose, the former or the latter?
                //The consequence of chossing the latter vector is that we will get "056..." which is not the best answer.
                if (greaterVector(nums1, i, nums2, j))result[k++] = nums1[i++];
                else result[k++] = nums2[j++];
            }
        }
        if (i >= nums1.size())while (j < nums2.size())result[k++] = nums2[j++];
        if (j >= nums2.size())while (i < nums1.size())result[k++] = nums1[i++];
        return result;
    }
    vector<int> maxNumber(vector<int>& nums1, vector<int>& nums2, int k)
    {
        //m, n is the nums1's and mums2's size respectively.
        int m = nums1.size();
        int n = nums2.size();
        //The variable biggest is aimed to store the biggest result we will get at every step.
        vector<int> biggest;
        //Firstly, we assume that all elememts of nums1 are included into the result,
        //then there are max(0, k - m) elements of which belong to nums2 in the result.
        //In the following loop, variable i represents the number of nums2's element which are put into the result.
        //The variable i varies in the range from max(0, k - m) to min(n, k).
        for (int i = (0 < (k - m) ? (k - m) : 0); i <= (n < k ? n : k); i++)
        {
            //Because there are i elements of nums2 which are put into the result, at least (k - i) nums1's elements must be counted.
            //We want to get a biggest number vector, so it's appropriate goal for us to get two number vectors from nums1 and nums2 whose size are (k - i) or i respectively.
            //Then we merge these two number vector, and compare it with thr biggest number vector we have got, update the variable used to store the biggest number vector alternatively.
            vector<int> maxvector1 = maxVector(nums1, k - i);
            vector<int> maxvector2 = maxVector(nums2, i);
            vector<int> curvector = mergeVector(maxvector1, maxvector2);
            if (greaterVector(curvector, 0, biggest, 0))biggest = curvector;
        }
        return biggest;
    }
};

www.sunshangyu.top

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值