Decremental String Concatenation - Problem

You're given an array of n strings and need to strategically combine them to create the shortest possible final string.

The key insight is in how strings are joined: when concatenating two strings x and y, if the last character of x matches the first character of y, one of the duplicate characters gets removed! This creates opportunities for optimization.

Join Operation Rules:

  • join("ab", "ba") = "aba" (duplicate 'b' removed)
  • join("ab", "cde") = "abcde" (no duplicates)

You must perform exactly n-1 join operations, starting with the first string. At each step, you can choose to either:

  1. Append the next word to your current result
  2. Prepend the next word to your current result

Your goal: Find the order that minimizes the final string length by maximizing character deletions.

Input & Output

example_1.py โ€” Basic joining
$ Input: words = ["aa", "ab", "bc"]
โ€บ Output: 4
๐Ÿ’ก Note: Start with "aa". We can append "ab" to get "aab" (length 3), then append "bc" to get "aabc" (length 4). The 'b' characters merge when joining "ab" and "bc".
example_2.py โ€” Optimal ordering
$ Input: words = ["ab", "b"]
โ€บ Output: 2
๐Ÿ’ก Note: Start with "ab". Append "b" to get "ab" + "b" = "ab" (the duplicate 'b' is removed). Final length is 2.
example_3.py โ€” No merging possible
$ Input: words = ["aaa", "c", "aba"]
โ€บ Output: 6
๐Ÿ’ก Note: No characters can be merged regardless of order, so we get the sum of all lengths: 3 + 1 + 2 = 6.

Constraints

  • 1 โ‰ค words.length โ‰ค 12
  • 1 โ‰ค words[i].length โ‰ค 20
  • words[i] consists of lowercase English letters only
  • Small input size makes exponential solutions viable

Visualization

Tap to expand
String Concatenation with Character Merging"ab""ba"+"aba"b=b merge!"xy""za"+"xyza"no mergeDecision Tree for words = ["aa", "ab", "bc"]"aa""aab""aabc"append "ab"append "bc"len: 3len: 4 (b merged)๐ŸŽฏ Key insight: Track only first/last chars + used words bitmask for optimal DP
Understanding the Visualization
1
Start with first word
Begin building our chain with words[0]
2
Consider merge opportunities
For each new word, check if last char of chain matches first char of word
3
Try both directions
Test both appending and prepending the new word
4
Choose optimal path
Select the direction that maximizes character savings
Key Takeaway
๐ŸŽฏ Key Insight: We only need to track the first and last characters of our current result string along with which words we've used, enabling efficient memoization without storing full strings.
Asked in
Google 15 Amazon 12 Meta 8 Microsoft 6
18.4K Views
Medium Frequency
~15 min Avg. Time
892 Likes
Ln 1, Col 1
Smart Actions
๐Ÿ’ก Explanation
AI Ready
๐Ÿ’ก Suggestion Tab to accept Esc to dismiss
// Output will appear here after running code
Code Editor Closed
Click the red button to reopen