Skip to content

1278. Palindrome Partitioning III

Description

You are given a string s containing lowercase letters and an integer k. You need to :

  • First, change some characters of s to other lowercase English letters.
  • Then divide s into k non-empty disjoint substrings such that each substring is a palindrome.

Return the minimal number of characters that you need to change to divide the string.

 

Example 1:

Input: s = "abc", k = 2
Output: 1
Explanation: You can split the string into "ab" and "c", and change 1 character in "ab" to make it palindrome.

Example 2:

Input: s = "aabbc", k = 3
Output: 0
Explanation: You can split the string into "aa", "bb" and "c", all of them are palindrome.

Example 3:

Input: s = "leetcode", k = 8
Output: 0

 

Constraints:

  • 1 <= k <= s.length <= 100.
  • s only contains lowercase English letters.

 

Solutions

Solution: Dynamic Programming

  • Time complexity: O(n2*k)
  • Space complexity: O(n2)

 

JavaScript

js
/**
 * @param {string} s
 * @param {number} k
 * @return {number}
 */
const palindromePartition = function (s, k) {
  const n = s.length;
  const changes = Array.from({ length: n }, () => Array.from({ length: n }, () => 0));

  for (let length = 2; length <= n; length++) {
    for (let start = 0; start + length - 1 < n; start++) {
      const end = start + length - 1;
      const isSame = s[start] === s[end];

      changes[start][end] = changes[start + 1][end - 1] + (isSame ? 0 : 1);
    }
  }
  const memo = new Map();

  const partition = (length, divide) => {
    if (divide === 1) return changes[0][length - 1];
    const key = `${length},${divide}`;

    if (memo.has(key)) return memo.get(key);
    let result = length;

    for (let index = divide - 1; index < length; index++) {
      const change = changes[index][length - 1];

      result = Math.min(partition(index, divide - 1) + change, result);
    }
    memo.set(key, result);
    return result;
  };

  return partition(n, k);
};

Released under the MIT license