Leetcode#140 Word Break II
动态规划题
令s[i..j]表示下标从i到j的子串,它的所有分割情况用words[i]表示
假设s[0..i]的所有分割情况words[i]已知。则s[0..i+1]的分割情况words[i+1] = words[k] + s[k+1..i+1],其中(有三个条件要满足)(1) 0 <= k <= i,(2) words[k]非空,(3) s[k+1..i+1]在字典中。
根据这个递推公式求解,有两种枚举方式:
1. 对于每个待求解的位置i,从0到i枚举所有的k,然后检验words[k]是否非空,以及s[k+1..i+1]是否在字典中
2. 对于每个待求解的位置i,枚举字典中的所有单词w,计算出k=i-w.length,然后检验是否0 <= k <= i,以及s[k+1..i+1]和w是否相等
两种方式各有优缺点,如果枚举k,则当原串s特别长的时候,效率比较低;如果枚举字典,当字典里的单词很多的时候,效率比较低。
感觉第一种方式(枚举k)更加自然一些。
最后需要注意的是,最坏情况下枚举的结果是2^n数量级的,此时如果把每个s[0..i]的所有分割情况都保存下来,内存会爆掉。所以只保存s[0..i]分割后的最后一个单词,最后用广搜构造所有解。
代码:
注:上面所说的"words"对应下面代码中的"record"
vector<string> wordBreak(string s, unordered_set<string> &dict) {
map<int, vector<string> > record;
int len = s.length();
// DP枚举
for (int i = ; i < len; i++) {
vector<string> words;
if (dict.find(s.substr(, i + )) != dict.end())
words.push_back(s.substr(, i + ));
for (int j = ; j <= i; j++) {
vector<string> pres = record[j - ];
string post = s.substr(j, i - j + );
if (!pres.empty() && dict.find(post) != dict.end()) {
words.push_back(post);
}
}
record.insert(pair<int, vector<string> >(i, words));
}
// BFS构造
vector<string> res;
queue<pair<int, string> > que;
for (auto r : record[len - ])
que.push(pair<int, string>(len - r.length(), r));
while (!que.empty()) {
pair<int, string> p = que.front();
que.pop();
if (p.first <= )
res.push_back(p.second);
else {
for (auto w : record[p.first - ])
que.push(pair<int, string>(p.first - w.length(), w + " " + p.second));
}
}
return res;
}
Leetcode#140 Word Break II的更多相关文章
- [LeetCode] 140. Word Break II 单词拆分II
Given a non-empty string s and a dictionary wordDict containing a list of non-empty words, add space ...
- leetcode 140. Word Break II ----- java
Given a string s and a dictionary of words dict, add spaces in s to construct a sentence where each ...
- Java for LeetCode 140 Word Break II
Given a string s and a dictionary of words dict, add spaces in s to construct a sentence where each ...
- leetcode 139. Word Break 、140. Word Break II
139. Word Break 字符串能否通过划分成词典中的一个或多个单词. 使用动态规划,dp[i]表示当前以第i个位置(在字符串中实际上是i-1)结尾的字符串能否划分成词典中的单词. j表示的是以 ...
- 140. Word Break II(hard)
欢迎fork and star:Nowcoder-Repository-github 140. Word Break II 题目: Given a non-empty string s and a d ...
- 【LeetCode】140. Word Break II
Word Break II Given a string s and a dictionary of words dict, add spaces in s to construct a senten ...
- [Leetcode Week9]Word Break II
Word Break II 题解 题目来源:https://leetcode.com/problems/word-break-ii/description/ Description Given a n ...
- 【leetcode】Word Break II
Word Break II Given a string s and a dictionary of words dict, add spaces in s to construct a senten ...
- 【LeetCode】140. Word Break II 解题报告(Python & C++)
作者: 负雪明烛 id: fuxuemingzhu 个人博客: http://fuxuemingzhu.cn/ 目录 题目描述 题目大意 解题方法 递归求解 日期 题目地址:https://leetc ...
随机推荐
- ES2015 ——let命令的暂时性死区
ES6新增了let命令,用来声明变量.它的用法类似于var,但是所声明的变量,只在let命令所在的代码块内有效. 和var不同的还有,let命令不存在变量提升,所以声明前调用变量,都会报错,这就涉及到 ...
- 仿淘宝颜色属性选择展示代码(jQuery)
模仿淘宝商品选择颜色和尺寸的效果,即选择商品颜色和尺寸的时候,把选择的颜色和尺寸放到一个页面容器里面,不足之处,还望指教. <!DOCTYPE HTML> <html lang=&q ...
- android 模拟按键事件
模拟按键事件可以提高代码的复用性,比如在一个edittext的回车事件里做的一些处理 在该edittext的另一个输入要做相同的处理时,模拟按键事件就非常方便了. 代码很简单,直接上代码: new T ...
- 【js & jquery】遮罩层实现禁止a、span、button等元素的鼠标事件
刚才在写一个界面,其中为了考虑背景图片的缘故,所以没用Button而是用的a标签 在点击之后应该禁用掉a元素,禁用对于button比较容易,加一个disabled就可以了 但是对于a却没有太好的办法, ...
- spring aop 使用注解方式总结
spring aop的注解方式:和xml的配置方式略有区别,详细如下: 1.首先还是建立需要的切面类:切面类里面定义好切点配置,以及所有的需要实现的通知方法. /** * */ package com ...
- 使用checked关键字处理“溢出”错误
在进行算术运算时,可以使用checked关键字有效处理溢出错误,使用checked关键字可能对程序的性能会有一点点的影响,这是一种以牺牲性能换取健康的做法. private void button1_ ...
- Objective-C-实例变量与属性的关系
当在一个类创建一个属性,Xcode编译器就会自动产生一个带下划线的同名实例变量: 一般来说,如果getter这个属性采用下划线的方式获取效率更高,而setter采用self.属性名更加合理. 读取实例 ...
- [转]Asp.net三种事务处理
事务处理是在数据处理时经常遇到的问题,经常用到的方法有以下三种总结整理如下:方法1:直接写入到sql 中在存储过程中使用 BEGIN TRANS, COMMIT TRANS, ROLLBACK TRA ...
- ASP运行流程(主要的类笔记)
个人笔记:参考汤姆大叔的MVC之前那些事系列整理 client端发送页面请求,被IIS的某个进程截获,它根据申请的页面后缀(.aspx)不同,调用不同的页面处理程序(.asp->asp.dll ...
- JSP的7个动作指令
动作指令与编译指令不同,编译指令是通知Servlet引擎的处理信息,而动作指令知识运行时的动作.编译指令在将JSP编译成Servlet时起作用,而处理指令通常可替换成JSP脚本,它知识JSP脚本的标准 ...