I've restructured the code slightly so it falls more in line with Python conventions:
def longest_palen(s):
return _longest_palen(s, 0, len(s) - 1, 0)
def _longest_palen(s, b, e, c):
if e < b:
return c
if b == e:
return c + 1
if s[b] == s[e]:
return max(_longest_palen(s, b + 1, e - 1, c + 2),
_longest_palen(s, b + 1, e, c),
_longest_palen(s, b, e - 1, c))
return max(
_longest_palen(s, b + 1, e, 0),
_longest_palen(s, b, e - 1, 0)
)
if __name__ == '__main__':
print(longest_palen("cyabbaxc")) # abba ("cyabbaxc"[2:6])
print(longest_palen("cabbacxc")) # cabbac ("cabbacxc"[:6])
print(longest_palen("cxcabbac")) # cabbac ("cxcabbac"[2:])
If the current first and last characters are the same there are four options:
- Both the current first and last character are in the Longest Palindrome.
- Input: "abba"
- Longest Palindrome: "abba" (4)
- Only the current first character is in the Longest Palindrome.
- Input: "cabbacxc"
- Longest Palindrome: "cabbac" (6)
- Even though the first and last character are "c" only the first is in the longest palindrome, future recursive steps need to include testing "cabbacx" and "cabbac" to get the correct answer.
- Only the current last character is in the Longest Palindrome.
- Input: "cxcabbac"
- Longest Palindrome: "cabbac" (6)
- Even though the first and last character are "c" only the last is in the longest palindrome, future recursive steps need to include testing "xcabbac" and "cabbac" to get the correct answer.
- Neither the current first nor last character are in the Longest Palindrome.
- Input: "cyabbaxc"
- Longest Palindrome: "abba" (4)
- This case is taken care of in a future recursive step as the next step will be "yabbax" where we'll handle testing both "yabba" and "abbax".
The reason you are running
c = _longestPalen(str, b + 1, e - 1, c + 2)
return bigger(c, bigger(_longestPalen(str, b + 1, e, c), _longestPalen(str, b, e - 1, c)))
or
return max(_longest_palen(s, b + 1, e - 1, c + 2),
_longest_palen(s, b + 1, e, c),
_longest_palen(s, b, e - 1, c))
in the modified implementation, is to consider all of these cases.
The pseudo code for this line is something like:
bigger(both_first_last_included, bigger(only_first_included, only_last_included))
In the modified implementation, I use max which I find to be clearer in understanding what operation is taking place.
max(both_first_last_included, only_first_included, only_last_included)