Top 15 LeetCode String Problem Solutions
01 Valid Anagram
# LeetCode 242: Valid Anagram
# https://leetcode.com/problems/valid-anagram/
def isAnagram(s: str, t: str) -> bool:
return sorted(s) == sorted(t)
02 Roman to Integer
# LeetCode 13: Roman to Integer
# https://leetcode.com/problems/roman-to-integer/
def romanToInt(s: str) -> int:
roman = {'I': 1, 'V': 5, 'X': 10, 'L': 50, 'C': 100, 'D': 500, 'M': 1000}
total = 0
prev = 0
for c in reversed(s):
if roman[c] < prev:
total -= roman[c]
else:
total += roman[c]
prev = roman[c]
return total
03 Longest Common Prefix
# LeetCode 14: Longest Common Prefix
# https://leetcode.com/problems/longest-common-prefix/
def longestCommonPrefix(strs: list[str]) -> str:
if not strs:
return ""
prefix = strs[0]
for word in strs[1:]:
while not word.startswith(prefix):
prefix = prefix[:-1]
return prefix
04 Valid Palindrome
# LeetCode 125: Valid Palindrome
# https://leetcode.com/problems/valid-palindrome/
def isPalindrome(s: str) -> bool:
s = ''.join(c.lower() for c in s if c.isalnum())
return s == s[::-1]
05 Reverse Words in a String
# LeetCode 151: Reverse Words in a String
# https://leetcode.com/problems/reverse-words-in-a-string/
def reverseWords(s: str) -> str:
return ' '.join(s.strip().split()[::-1])
06 Implement strStr
# LeetCode 28: Find the Index of the First Occurrence in a String
# https://leetcode.com/problems/implement-strstr/
def strStr(haystack: str, needle: str) -> int:
return haystack.find(needle)
07 Longest Substring Without Repeating Characters
# LeetCode 3: Longest Substring Without Repeating Characters
# https://leetcode.com/problems/longest-substring-without-repeating-characters/
def lengthOfLongestSubstring(s: str) -> int:
char_index = {}
left = max_len = 0
for right, c in enumerate(s):
if c in char_index and char_index[c] >= left:
left = char_index[c] + 1
char_index[c] = right
max_len = max(max_len, right - left + 1)
return max_len
08 Minimum Window Substring
# LeetCode 76: Minimum Window Substring
# https://leetcode.com/problems/minimum-window-substring/
from collections import Counter
def minWindow(s: str, t: str) -> str:
if not s or not t:
return ""
t_count = Counter(t)
window = {}
have, need = 0, len(t_count)
res, res_len = [-1, -1], float("inf")
left = 0
for right, c in enumerate(s):
window[c] = window.get(c, 0) + 1
if c in t_count and window[c] == t_count[c]:
have += 1
while have == need:
if (right - left + 1) < res_len:
res = [left, right]
res_len = right - left + 1
window[s[left]] -= 1
if s[left] in t_count and window[s[left]] < t_count[s[left]]:
have -= 1
left += 1
l, r = res
return s[l:r+1] if res_len != float("inf") else ""
09 Group Anagrams
# LeetCode 49: Group Anagrams
# https://leetcode.com/problems/group-anagrams/
from collections import defaultdict
def groupAnagrams(strs: list[str]) -> list[list[str]]:
anagrams = defaultdict(list)
for word in strs:
key = tuple(sorted(word))
anagrams[key].append(word)
return list(anagrams.values())
10 Longest Palindromic Substring
# LeetCode 5: Longest Palindromic Substring
# https://leetcode.com/problems/longest-palindromic-substring/
def longestPalindrome(s: str) -> str:
res = ""
for i in range(len(s)):
for j in [i, i+1]:
l, r = i, j
while l >= 0 and r < len(s) and s[l] == s[r]:
if (r - l + 1) > len(res):
res = s[l:r+1]
l -= 1
r += 1
return res
11 Palindrome Partitioning
# LeetCode 131: Palindrome Partitioning
# https://leetcode.com/problems/palindrome-partitioning/
def partition(s: str) -> list[list[str]]:
res = []
def is_palindrome(word):
return word == word[::-1]
def backtrack(start, path):
if start == len(s):
res.append(path[:])
return
for end in range(start+1, len(s)+1):
if is_palindrome(s[start:end]):
backtrack(end, path + [s[start:end]])
backtrack(0, [])
return res
12 Zigzag Conversion
# LeetCode 6: Zigzag Conversion
# https://leetcode.com/problems/zigzag-conversion/
def convert(s: str, numRows: int) -> str:
if numRows == 1 or numRows >= len(s):
return s
rows = [''] * numRows
idx, step = 0, 1
for c in s:
rows[idx] += c
if idx == 0:
step = 1
elif idx == numRows - 1:
step = -1
idx += step
return ''.join(rows)
13 Multiply Strings
# LeetCode 43: Multiply Strings
# https://leetcode.com/problems/multiply-strings/
def multiply(num1: str, num2: str) -> str:
if num1 == "0" or num2 == "0":
return "0"
res = [0] * (len(num1) + len(num2))
for i in range(len(num1)-1, -1, -1):
for j in range(len(num2)-1, -1, -1):
mul = int(num1[i]) * int(num2[j])
pos1, pos2 = i + j, i + j + 1
total = mul + res[pos2]
res[pos2] = total % 10
res[pos1] += total // 10
result = ''.join(map(str, res)).lstrip('0')
return result
14 Count and Say
# LeetCode 38: Count and Say
# https://leetcode.com/problems/count-and-say/
def countAndSay(n: int) -> str:
result = "1"
for _ in range(n - 1):
new_result = ""
i = 0
while i < len(result):
count = 1
while i + 1 < len(result) and result[i] == result[i + 1]:
i += 1
count += 1
new_result += str(count) + result[i]
i += 1
result = new_result
return result
15 Decode Ways
# LeetCode 91: Decode Ways
# https://leetcode.com/problems/decode-ways/
def numDecodings(s: str) -> int:
if not s or s[0] == '0':
return 0
dp = [0] * (len(s)+1)
dp[0] = dp[1] = 1
for i in range(2, len(s)+1):
if s[i-1] != '0':
dp[i] += dp[i-1]
if 10 <= int(s[i-2:i]) <= 26:
dp[i] += dp[i-2]
return dp[-1]