将一串字符分成有效的单词

时间:2013-01-05 14:39:12

标签: java algorithm data-structures recursion dynamic-programming

我正在阅读动态编程问题。问题如下:

  

将长度为n的字符串转换为有效序列   话。假设有一个数据结构告诉您是否有字符串   在恒定时间内是一个有效的单词。

我在某种程度上解决了我的问题,但我读到的解决方案如下:

  

创建一个表T [N],表示如果子串,则T [i]为真   [0 ... i]可以分解成一系列有效的单词。如果是,则[[]]为真   存在j,0 <= j <= k-1其中T [j]为真并且S(j,k)是有效的   单词

这是DP的经典表述,但不是错吗?不应该是:

  如果存在j,0 <=> j <= k-1,则T [i]为真,其中T [j]为真并且   S( j + 1 ,k)是有效字 OR S(0,i)是有效字

否则我不知道如何构建表格,因为例如字符串:itsthe如果我们不考虑T[2] = true,我们将永远不会its }是一个单词,下一个序列是the,即S(2+1, N),j = 2 我在这儿吗?但是,我们怎样才能找到实际的词呢? 我为理解而做的示例代码(s.substring(i,j)从java中的i including j-1返回子字符串):

int i = 0  
for(; i < s.length(); i++){  
   for(int j = 0; j > i; j++){  
       if(T[j] && dictionary.contains(s.substring(j + 1, i)){  
             T[i] = true;
             break;  
       }  
    }  
    if(dictionary.contains(s.substring(0, i + 1)){  
         T[i] = true;  
    }  
}  

2 个答案:

答案 0 :(得分:1)

你的所有更正都是正确的。

如果您想重建实际单词,请添加一个表格数组,该数组会告诉您用于将t[i]设置为true的最后一个字长。让我们调用这个数组L[i]

  如果存在j,0 <=> j <= k-1,则T [i]为真,其中T [j]为真并且   S(j + 1,k)是有效字OR S(0,i)是有效字吗? 在第一个   如果您在后者L[i] = j中设置了L[i] = i

然后添加您需要从L[n]递回的结尾,其中n是给定字符串的总长度。

答案 1 :(得分:0)

这取决于您的符号意味着什么,特别是选择子序列。你混合方括号和圆括号,“substring [0 ... i]”和“S(j + 1,k)”;我建议我们总是包括左手索引而不是右手索引。有时通过在左侧使用方括号和在右侧使用圆括号来明确这一点:S [0 ... i)。

如果我们这样做,那么原始措辞几乎正确;在i和k之间存在一些混淆,我认为这应该是相同的,并且i = 0的情况未得到正确处理。 (在相关的说明中,我认为你的修改也可能无法正确处理n = 0(空字符串)的情况。)

Create a table T[N] which says that T[i] is true if the substring S[0...i)
can be broken into a sequence of valid words. T[i] is true iff i = 0 OR
(there exists a j, 0<=j<i, where T[j] is true AND S[j...i) is a valid word).