2017-03-24 41 views
1

我试图将文本输入转换为保留其结构的嵌套列表。目前我有一个函数需要一个文本和一个期望的“深度”,并输出这个深度的嵌套列表,在每一个新行,句子或单词处打破文本。如何将文本转换为嵌套列表

def text_split(text, depth): 
    depth_list = [' ', '.', '\n'] 
    if isinstance(text, str): 
     text = text.strip('. ') 
     text = text.split(depth_list[depth]) 
    if depth >= 0: 
     depth -= 1 
     for ix, item in enumerate(text): 
       item = item.strip('. ') 
       text[ix] = text_split(item, depth) 
    return text 

这需要文本,如

text1 = """acabei de ler um livro. um diário. 
mas a liberdade sempre chamou fountaine mais forte. 
a cada viagem fountaine ía mais longe. aprendeu a andar de bicicleta e viajou o sul da frança. 

esse é o tipo de pergunta feita na última edição do prêmio Loebner, em que participantes precisam responder à algumas questões feitas pelo júri. 

o que tem de especial nessa competição é que ela não é para humanos, mas sim para robôs. o prêmio Loebner é uma implementação do teste de Turing. 

""" 

[ [[['acabei'], ['de'], ['ler'], ['um'], ['livro']], [['um'], ['diário']]], 
[ [ ['mas'], 
     ['a'], 
     ['liberdade'], 
     ['sempre'], 
     ['chamou'], 
     ['fountaine'], 
     ['mais'], 
     ['forte']]], 
[ [ ['a'], 
     ['cada'], 
     ['viagem'], 
     ['fountaine'], 
     ['ía'], 
     ['mais'], 
     ['longe']], 
    [ ['aprendeu'], 
     ['a'], 
     ['andar'], 
     ['de'], 
     ['bicicleta'], 
     ['e'], 
     ['viajou'], 
     ['o'], 
     ['sul'], 
     ['da'], 
     ['frança']]], 
[[['']]], ... ]]]] 

现在这可能不是这样做的最好,最优雅的方式,它有一些问题,如在\n被分割之后出现的[[['']]](这可以通过使用.splitlines()来解决,但我无法找到一种很好的调用方式这个方法在递归函数中)。

这样做的更好方法是什么?我应该使用嵌套列表吗? (我打算在此后迭代)。感谢您的建议!

+0

你为什么希望所有的深度,例如为什么列表中只有一个单词呢? – AChampion

+0

@AChampion确实,这是没有必要保持结构!这不是要求。感谢您指出! –

回答

1

这是我能想出以满足您的需求的最佳:

text = [] 
for line in text1.split('\n'): 
    sentences = [] 
    for sentence in line.split('.'): 
    words = [] 
    for word in sentence.split(' '): 
     if len(word.strip()) > 0: # make sure we are adding something 
     words.append(word.strip()) 
    if len(words) > 0: 
     sentences.append(words) 
    if len(sentences) > 0: 
    text.append(sentences) 

利用这一点,我们有数组定义良好的结构,我们可以肯定的是,我们没有任何空白或空阵列。此外,在这里使用递归并不是一件好事,因为你有一个清晰的文本结构。你知道递归的深度不会超过3级。另外,如果你想要一个递归的版本,你应该在你的问题中说明它,并清除需求。

+0

更清晰!我去了一个递归函数,因为我想我可能会在稍后扩展我的depth_list,但是想一想,我认为它不会比_deeper_更进一步:P谢谢! –

+0

没问题!请记住接受答案,如果它回答了你的问题 – meyer9

+0

我做了一些改变 'for line in text.splitlines():'splits直接删除\ n \ n(不需要长度检查) '如果stripped_word:'比检查长度快(并且结果相同,我希望) –

1

您可以使用嵌套列表理解只是用你的标准拆分:

>>> [[s.split() for s in line.split('.') if s] for line in text1.split('\n') if line] 
[[['acabei', 'de', 'ler', 'um', 'livro'], ['um', 'diário']], 
[['mas', 'a', 'liberdade', 'sempre', 'chamou', 'fountaine', 'mais', 'forte']], 
[['a', 'cada', 'viagem', 'fountaine', 'ía', 'mais', 'longe'], 
    ['aprendeu', 'a', 'andar', 'de', 'bicicleta', 'e', 'viajou', 'o', 'sul', 'da', 'frança']], 
... 
+0

感谢您的帮助!我只增加了另一层理解,以便我可以从单词中删除',',并将split('\ n')'更改为'splitlines()',因为它似乎更通用: '[[[w.strip(',。;')for s.split()if w] for s in line.split('。')if s] for line in text.splitlines()if line] ' –