From 01490da048e455b67f8919873f6fc7fb851a03d6 Mon Sep 17 00:00:00 2001 From: Asterisk <44215173+casnz1601@users.noreply.github.com> Date: Mon, 11 Oct 2021 13:30:42 +0800 Subject: [PATCH] =?UTF-8?q?Update=200093.=E5=A4=8D=E5=8E=9FIP=E5=9C=B0?= =?UTF-8?q?=E5=9D=80.md?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit python3代码修正和补充注释 --- problems/0093.复原IP地址.md | 65 ++++++++++++++++++++------------- 1 file changed, 40 insertions(+), 25 deletions(-) diff --git a/problems/0093.复原IP地址.md b/problems/0093.复原IP地址.md index 4e56ddc4..1d8ad296 100644 --- a/problems/0093.复原IP地址.md +++ b/problems/0093.复原IP地址.md @@ -342,32 +342,47 @@ class Solution: ``` python3: -```python -class Solution(object): - def restoreIpAddresses(self, s): - """ - :type s: str - :rtype: List[str] - """ - ans = [] - path = [] - def backtrack(path, startIndex): - if len(path) == 4: - if startIndex == len(s): - ans.append(".".join(path[:])) - return - for i in range(startIndex+1, min(startIndex+4, len(s)+1)): # 剪枝 - string = s[startIndex:i] - if not 0 <= int(string) <= 255: - continue - if not string == "0" and not string.lstrip('0') == string: - continue - path.append(string) - backtrack(path, i) - path.pop() +```python3 +class Solution: + def __init__(self): + self.result = [] - backtrack([], 0) - return ans``` + def restoreIpAddresses(self, s: str) -> List[str]: + ''' + 本质切割问题使用回溯搜索法,本题只能切割三次,所以纵向递归总共四层 + 因为不能重复分割,所以需要start_index来记录下一层递归分割的起始位置 + 添加变量point_num来记录逗号的数量[0,3] + ''' + self.result.clear() + if len(s) > 12: return [] + self.backtracking(s, 0, 0) + return self.result + + def backtracking(self, s: str, start_index: int, point_num: int) -> None: + # Base Case + if point_num == 3: + if self.is_valid(s, start_index, len(s)-1): + self.result.append(s[:]) + return + # 单层递归逻辑 + for i in range(start_index, len(s)): + # [start_index, i]就是被截取的子串 + if self.is_valid(s, start_index, i): + s = s[:i+1] + '.' + s[i+1:] + self.backtracking(s, i+2, point_num+1) # 在填入.后,下一子串起始后移2位 + s = s[:i+1] + s[i+2:] # 回溯 + else: + # 若当前被截取的子串大于255或者大于三位数,直接结束本层循环 + break + + def is_valid(self, s: str, start: int, end: int) -> bool: + if start > end: return False + # 若数字是0开头,不合法 + if s[start] == '0' and start != end: + return False + if not 0 <= int(s[start:end+1]) <= 255: + return False + return True ```