Word Break II

本文介绍了一种基于字典匹配的字符串拆分算法,通过构建有效子序列判断矩阵并寻找所有可能的有效路径,实现将字符串拆分为字典中存在的单词。文章详细解释了算法的具体实现过程,并分享了在不同编译器环境下遇到的问题及解决方案。

问题:

Given a string s and a dictionary of words dict, add spaces in s to construct a sentence where each word is a valid dictionary word.

Return all such possible sentences.

For example, given
s = "catsanddog",
dict = ["cat", "cats", "and", "sand", "dog"].

A solution is ["cats and dog", "cat sand dog"].

解析:

其实我是先看到这个题目,做了,后来才做wordbreak 的。所以具体思路和word break一样。先构建有效子序列的判断矩阵,之后找有效路径,所不同的是这次要保存有效路径。

所以主要改了最后的递归函数。但是一直没有A让我烦心好久。后来发现是因为set本身的原因,set本身按从小到大排序,结果oj上的结果是按从大到小。我以为是按字典序,还特意去写了字典序呢。

class Solution {
vector<string> result;
int **judge;
int *size;
 void addResult(string str, int start, string item)
 {
	 if(start == str.length())
	 {
		 result.push_back(item.substr(0,item.length()));
	 }
	 else
	 {
		 for(int k = 0; k < size[start]; k++)
		 {			 
			int end = judge[start][k];
			if(item.length() > 0  && item.substr(item.length()-1,1).compare(" ") != 0) item +=" ";
			 item += str.substr(start,end-start+1);
			addResult(str, end+1,item);
			item = item.substr(0,item.length()-end+start-1);
			 
		 }
	 }
 }
public:
 vector<string> wordBreak(string s, unordered_set<string> &dict) 
 {
	 if(s.length() == 0 || dict.size() == 0) return result;
	 int len = s.length();
	 judge = new int*[len];
	 size = new int[len];
	 memset(size, 0, len*sizeof(int));
	 bool flag = false;
	 for(int i = 0; i < len; i++)
	 {
		 judge[i] = new int[len];
		 for(unordered_set<string>::iterator it = dict.begin(); it != dict.end(); it++)
		 {
			 int wordlen = it->length();
			 if(i + wordlen <= len &&  
				 it->compare(s.substr(i,wordlen)) == 0)
			 {
				 judge[i][size[i]++] = i+ wordlen-1;
				 if(i + wordlen == len) flag = true;
			 }
		 }
	 }
	 if(flag == true) // 存在
		addResult(s,0,"");
	 for(int i = 0; i < len; i++)
		 delete judge[i];
	 delete judge;
	 delete size;
	 vector<string> res;
	 for(int i = result.size() - 1; i >=0; i--)
	 	res.push_back(result[i]);
	 return res;
}

};

今天总算把前两天积压的问题A过了,还发现了一个意外就是VS编译器和DevC++在处理set上市不一样的。VS中unorderset遍历可以按原本顺序,Dev中如果没导入库,仅仅支持set,而且会有默认排序,所以无法得到原本输入的顺序。伤不起的累了
### CSS `word-break` 属性详解 #### 定义与作用 `word-break` 是一个用于控制单词内断行行为的 CSS 属性。该属性定义了如何处理过长而不适合其容器宽度的文字,以及在何种情况下允许这些文字被拆分到多行显示。 #### 可选值及其效果 - **normal**: 使用默认规则来决定在哪里可以折行。通常只会在空格处或连字符上换行[^1]。 - **break-all**: 允许在任何字符间断开,即使是在非空白字符之间也会强制换行。这种设置对于包含大量不可分割长词的语言(如中文、日文)特别有用[^2]。 - **keep-all**: 防止除字典定义外的地方发生断裂;适用于不允许随意切割词语的情况,比如英文中的专有名词等[^3]. #### 实际应用案例 当页面布局中有固定大小但可能容纳不下某些较长文本内容时,可以通过调整此样式属性使溢出部分合理地分布于下一行而不是超出边界造成视觉混乱: ```html <div style="width: 200px; border: solid;"> <!-- 这里放置一段很长且无自然间隔符的日语字符串 --> </div> ``` 为了确保上述 HTML 中的内容能够在指定宽度范围内正确展示而不会破坏整体设计美感,则可以在对应的 `<style>` 或外部样式表文件中加入如下声明: ```css /* 设置 div 的 word-break 行为 */ div { word-break: break-all; } ``` 这样就可以让那些超宽却不含合法打断位置的文字也能按照预期表现出来,既不破坏原有结构又实现了良好的用户体验[^4]。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值