LeetCode(93): 复原IP地址
Medium!
题目描述:
给定一个只包含数字的字符串,复原它并返回所有可能的 IP 地址格式。
示例:
输入: "25525511135"
输出:["255.255.11.135", "255.255.111.35"]
解题思路:
IP地址由32位二进制数组成,为便于使用,常以XXX.XXX.XXX.XXX形式表现,每组XXX代表小于或等于255的10进制数。所以说IP地址总共有四段,每一段可能有一位,两位或者三位,范围是[0, 255],题目明确指出输入字符串只含有数字,所以当某段是三位时,我们要判断其是否越界(>255),还有一点很重要的是,当只有一位时,0可以成某一段,如果有两位或三位时,像 00, 01, 001, 011, 000等都是不合法的,所以我们还是需要有一个判定函数来判断某个字符串是否合法。
这道题其实也可以看做是字符串的分段问题,在输入字符串中加入三个点,将字符串分为四段,每一段必须合法,求所有可能的情况。根据目前刷了这么多题,得出了两个经验,一是只要遇到字符串的子序列或配准问题首先考虑动态规划DP,二是只要遇到需要求出所有可能情况首先考虑用递归。这道题并非是求字符串的子序列或配准问题,更符合第二种情况,所以我们要用递归来解。我们用k来表示当前还需要分的段数,如果k = 0,则表示三个点已经加入完成,四段已经形成,若这时字符串刚好为空,则将当前分好的结果保存。若k != 0, 则对于每一段,我们分别用一位,两位,三位来尝试,分别判断其合不合法,如果合法,则调用递归继续分剩下的字符串,最终和求出所有合法组合。
C++解法一:
 class Solution {
 public:
     vector<string> restoreIpAddresses(string s) {
         vector<string> res;
         restore(s, , "", res);
         return res;
     }
     void restore(string s, int k, string out, vector<string> &res) {
         if (k == ) {
             if (s.empty()) res.push_back(out);
         }
         else {
             for (int i = ; i <= ; ++i) {
                 if (s.size() >= i && isValid(s.substr(, i))) {
                     if (k == ) restore(s.substr(i), k - , out + s.substr(, i), res);
                     else restore(s.substr(i), k - , out + s.substr(, i) + ".", res);
                 }
             }
         }
     }
     bool isValid(string s) {
         if (s.empty() || s.size() >  || (s.size() >  && s[] == '')) return false;
         int res = atoi(s.c_str());
         return res <=  && res >= ;
     }
 };
我们也可以省掉isValid函数,直接在调用递归之前用if语句来滤掉不符合题意的情况,这里面用了k != std::to_string(val).size(),其实并不难理解,比如当k=3时,说明应该是个三位数,但如果字符是"010",那么转为整型val=10,再转回字符串就是"10",此时的长度和k值不同了,这样就可以找出不合要求的情况了。
C++解法二:
 class Solution {
 public:
     vector<string> restoreIpAddresses(string s) {
         vector<string> res;
         helper(s, , "", res);
         return res;
     }
     void helper(string s, int n, string out, vector<string>& res) {
         if (n == ) {
             if (s.empty()) res.push_back(out);
         } else {
             for (int k = ; k < ; ++k) {
                 if (s.size() < k) break;
                 int val = atoi(s.substr(, k).c_str());
                 if (val >  || k != std::to_string(val).size()) continue;
                 helper(s.substr(k), n + , out + s.substr(, k) + (n ==  ? "" : "."), res);
             }
         }
     }
 };
由于每段数字最多只能有三位,而且只能分为四段,所以情况并不是很多,我们可以使用暴力搜索的方法,每一段都循环1到3,然后当4段位数之和等于原字符串长度时,我们进一步判断每段数字是否不大于255,然后滤去不合要求的数字,加入结果中即可。
C++解法三:
 class Solution {
 public:
     vector<string> restoreIpAddresses(string s) {
         vector<string> res;
         for (int a = ; a < ; ++a)
         for (int b = ; b < ; ++b)
         for (int c = ; c < ; ++c)
         for (int d = ; d < ; ++d)
             if (a + b + c + d == s.size()) {
                 int A = stoi(s.substr(, a));
                 int B = stoi(s.substr(a, b));
                 int C = stoi(s.substr(a + b, c));
                 int D = stoi(s.substr(a + b + c, d));
                 if (A <=  && B <=  && C <=  && D <= ) {
                     string t = to_string(A) + "." + to_string(B) + "." + to_string(C) + "." + to_string(D);
                     if (t.size() == s.size() + ) res.push_back(t);
                 }
             }
         return res;
     }
 };
LeetCode(93): 复原IP地址的更多相关文章
- Java实现 LeetCode 93 复原IP地址
		93. 复原IP地址 给定一个只包含数字的字符串,复原它并返回所有可能的 IP 地址格式. 示例: 输入: "25525511135" 输出: ["255.255.11. ... 
- leetcode 93 复原IP地址
		IP地址,分成四段,每段是0-255,按照每段的长度分别为1,2,3下一段长度分别1,2,3再下一段......进行递归遍历,能满足条件的假如res中.比较难想到的就是假如有一段是三位的010是不符合 ... 
- LeetCode 93. 复原IP地址(Restore IP Addresses)
		题目描述 给定一个只包含数字的字符串,复原它并返回所有可能的 IP 地址格式. 示例: 输入: "25525511135" 输出: ["255.255.11.135&qu ... 
- LeetCode:复原IP地址【93】
		LeetCode:复原IP地址[93] 题目描述 给定一个只包含数字的字符串,复原它并返回所有可能的 IP 地址格式. 示例: 输入: "25525511135" 输出: [&qu ... 
- leetcode刷题-93复原IP地址
		题目 给定一个只包含数字的字符串,复原它并返回所有可能的 IP 地址格式. 有效的 IP 地址正好由四个整数(每个整数位于 0 到 255 之间组成),整数之间用 '.' 分隔. 示例: 输入: &q ... 
- Leetcode 93.复制IP地址
		复制IP地址 给定一个只包含数字的字符串,复原它并返回所有可能的 IP 地址格式. 示例: 输入: "25525511135" 输出: ["255.255.11.135& ... 
- 93复原IP地址。
		from typing import List# 这道题不是很难,但是限制条件有很多.# 用递归的方法可以很容易的想到.只需要四层递归就好了.# 每次进行加上限制条件.过滤每一层就好了..class ... 
- 93. 复原 IP 地址
		做题思路or感想 这种字符串切割的问题都可以用回溯法来解决 递归三部曲: 递归参数 因为要切割字符串,所以要用一个startIndex来控制子串的开头位置,即是会切割出一个范围是[startIndex ... 
- 93. 复原IP地址
		题目描述: 给定一个只包含数字的字符串,复原它并返回所有可能的 IP 地址格式. 示例: 输入: "25525511135" 输出: ["255.255.11.135&q ... 
- [LeetCode] Restore IP Addresses  复原IP地址
		Given a string containing only digits, restore it by returning all possible valid IP address combina ... 
随机推荐
- computed,methods,watch
			加载顺序: 在官方文档中,强调了computed区别于method最重要的两点 computed是属性调用,而methods是函数调用 computed带有缓存功能,而methods不是 计算属性是基 ... 
- 【blog】SpringMVC接收数组
			页面 var idsArray = new Array(); idsArray.push(userId); SpringMVC @RequestParam(value = "ids[]&qu ... 
- 什么是java字节码?
			什么是java字节码? java字码是java源程序代码的一种较为低级的表示.Java编译器将源代码编译成字码后,就可以Java解释器执行 
- 下面那些是无效的Java标识符?
			下面那些是无效的Java标识符?为什么? a.RESULT b.result c.12345 d.x12345y e.black&white f.answer_7 c和e是无效的,因为标识符不 ... 
- flask 连接mysql及基本操作
			#导入第三方连接库sql点金术 from flask_sqlalchemy import SQLAlchemy #建立对象 app = Flask(__name__) #载入配置文件 app.conf ... 
- 【VMware vSphere】ESXi系统设置静态IP
			写在前面: 为了方便管理,一般将ESXi系统的IP设置为静态 ESXi6.5系统和6.0系统类似,这里以ESXi6.0系统为例 1, 进入系 ... 
- Linker Scripts3--MEMORY Command
			1.前言 链接器的默认配置允许所有有效内存的分配,你可以使用MEMORY命令来重新定义它 2.MEMORY命令 MEMORY命令描述了一个内存块的位置和大小.你可以用它来描述哪块内存区域可以被链接器使 ... 
- Delphi 实现自动更新
			Delphi 通用程序自动更新升级:http://www.delphitop.com/html/wangluo/2968.html https://www.cnblogs.com/hnxxcxg/p/ ... 
- Linux内核之进程地址空间
			Linux内核之进程地址空间 内核中的函数以相当直接了当的方式获得动态内存: __get_free_pages 或 alloc_pages从分区页框分配器中获得页框; kmem_cache_alloc ... 
- page.isvalid
			背景 看到这个标题,想了半天,为啥用的.应该是当初前台要动态增加行这个事情,当初用.net真是用傻了,竟然对html.aspx原理不大清楚,对于html也想着后台生成.真是弱智啊.谈到这里,想到c#这 ... 
