You are given two strings word1
and word2
. You want to construct a string merge
in the following way: while either word1
or word2
are non-empty, choose one of the following options:
word1
is non-empty, append the first character in word1
to merge
and delete it from word1
.
word1 = "abc"
and merge = "dv"
, then after choosing this operation, word1 = "bc"
and merge = "dva"
.word2
is non-empty, append the first character in word2
to merge
and delete it from word2
.
word2 = "abc"
and merge = ""
, then after choosing this operation, word2 = "bc"
and merge = "a"
.Return the lexicographically largest merge
you can construct.
A string a
is lexicographically larger than a string b
(of the same length) if in the first position where a
and b
differ, a
has a character strictly larger than the corresponding character in b
. For example, "abcd"
is lexicographically larger than "abcc"
because the first position they differ is at the fourth character, and d
is greater than c
.
Example 1:
Input: word1 = "cabaa", word2 = "bcaaa" Output: "cbcabaaaaa" Explanation: One way to get the lexicographically largest merge is: - Take from word1: merge = "c", word1 = "abaa", word2 = "bcaaa" - Take from word2: merge = "cb", word1 = "abaa", word2 = "caaa" - Take from word2: merge = "cbc", word1 = "abaa", word2 = "aaa" - Take from word1: merge = "cbca", word1 = "baa", word2 = "aaa" - Take from word1: merge = "cbcab", word1 = "aa", word2 = "aaa" - Append the remaining 5 a's from word1 and word2 at the end of merge.
Example 2:
Input: word1 = "abcabc", word2 = "abdcaba" Output: "abdcabcabcaba"
Constraints:
1 <= word1.length, word2.length <= 3000
word1
and word2
consist only of lowercase English letters.This problem asks to find the lexicographically largest string that can be formed by merging two given strings, word1
and word2
. We can only append the next character from either word1
or word2
at each step.
Approach:
The core idea is to greedily choose the lexicographically larger suffix at each step. We compare suffixes of word1
and word2
starting from the current indices. The suffix that is lexicographically larger determines which character gets appended to the result. This continues until one of the strings is exhausted; then, the remaining characters from the other string are appended.
Algorithm:
Initialization: Initialize two pointers i
and j
to 0, representing the current indices in word1
and word2
, respectively. Initialize an empty string ans
to store the result.
Iteration: While both i
and j
are within the bounds of their respective strings:
word1[i:]
and word2[j:]
.word1[i:]
is lexicographically larger, append word1[i]
to ans
and increment i
.word2[j]
to ans
and increment j
.Remaining Characters: After the loop, one of the strings might have remaining characters. Append the remaining characters from the non-exhausted string to ans
.
Return: Return the string ans
.
Time Complexity Analysis:
The algorithm iterates through the strings at most once. The compareTo
operation (or equivalent string comparison) in each iteration takes O(min(len(word1[i:]),len(word2[j:]))) in the worst case. However, in the aggregate, the comparisons done across the entire process is bounded by O(m+n), where m and n are lengths of word1
and word2
, respectively. This is because each character is only considered at most twice (once for each string). Therefore, the overall time complexity is O(m + n).
Space Complexity Analysis:
The space used is dominated by the ans
string, which has a maximum length of m + n
. Therefore, the space complexity is O(m + n).
Code Examples (with minor optimizations):
The provided code examples in Python, Java, C++, Go, TypeScript, Rust, and C all implement this approach efficiently. The Python and Java examples use built-in string comparison functions (>
, compareTo
) for efficiency. The other examples use byte-wise comparison (or equivalent). Note that the C example manually allocates memory and requires freeing the memory after use to avoid memory leaks. All implementations strive for the O(m+n) time and space complexity.