2012-10-20 9 views
5

Chciałbym zmodyfikować poniższy skrypt, aby tworzył akapity z losowej liczby zdań generowanych przez skrypt. Innymi słowy, przed dodaniem nowego wiersza połącz losową liczbę (np. 1-5) zdań.Jak tworzyć akapity z wyjścia łańcucha Markowa?

Skrypt działa poprawnie tak jak jest, ale wyniki są krótkimi zdaniami oddzielonymi znakiem nowej linii. Chciałbym zebrać kilka zdań w akapity.

Wszelkie pomysły dotyczące najlepszych praktyk? Dzięki.

""" 
    from: http://code.activestate.com/recipes/194364-the-markov-chain-algorithm/?in=lang-python 
""" 

import random; 
import sys; 

stopword = "\n" # Since we split on whitespace, this can never be a word 
stopsentence = (".", "!", "?",) # Cause a "new sentence" if found at the end of a word 
sentencesep = "\n" #String used to seperate sentences 


# GENERATE TABLE 
w1 = stopword 
w2 = stopword 
table = {} 

for line in sys.stdin: 
    for word in line.split(): 
     if word[-1] in stopsentence: 
      table.setdefault((w1, w2), []).append(word[0:-1]) 
      w1, w2 = w2, word[0:-1] 
      word = word[-1] 
     table.setdefault((w1, w2), []).append(word) 
     w1, w2 = w2, word 
# Mark the end of the file 
table.setdefault((w1, w2), []).append(stopword) 

# GENERATE SENTENCE OUTPUT 
maxsentences = 20 

w1 = stopword 
w2 = stopword 
sentencecount = 0 
sentence = [] 

while sentencecount < maxsentences: 
    newword = random.choice(table[(w1, w2)]) 
    if newword == stopword: sys.exit() 
    if newword in stopsentence: 
     print ("%s%s%s" % (" ".join(sentence), newword, sentencesep)) 
     sentence = [] 
     sentencecount += 1 
    else: 
     sentence.append(newword) 
    w1, w2 = w2, newword 

EDIT 01:

Ok, mam sklecony prostą „paragraf opakowanie”, który działa dobrze zebrać zdania w akapity, ale to pomieszane ze wyjściu generator zdań - uzyskuję nadmierną powtarzalność pierwszych słów, na przykład, między innymi.

Ale przesłanką jest dźwięk; Po prostu muszę dowiedzieć się, dlaczego na funkcjonalność pętli zdań wpłynęło dodanie pętli akapitu. Proszę doradzić, jeśli widzisz problem:

### 
# usage: $ python markov_sentences.py <input.txt> output.txt 
# from: http://code.activestate.com/recipes/194364-the-markov-chain-algorithm/?in=lang-python 
### 

import random; 
import sys; 

stopword = "\n" # Since we split on whitespace, this can never be a word 
stopsentence = (".", "!", "?",) # Cause a "new sentence" if found at the end of a word 
paragraphsep = "\n\n" #String used to seperate sentences 


# GENERATE TABLE 
w1 = stopword 
w2 = stopword 
table = {} 

for line in sys.stdin: 
    for word in line.split(): 
     if word[-1] in stopsentence: 
      table.setdefault((w1, w2), []).append(word[0:-1]) 
      w1, w2 = w2, word[0:-1] 
      word = word[-1] 
     table.setdefault((w1, w2), []).append(word) 
     w1, w2 = w2, word 
# Mark the end of the file 
table.setdefault((w1, w2), []).append(stopword) 

# GENERATE PARAGRAPH OUTPUT 
maxparagraphs = 10 
paragraphs = 0 # reset the outer 'while' loop counter to zero 

while paragraphs < maxparagraphs: # start outer loop, until maxparagraphs is reached 
    w1 = stopword 
    w2 = stopword 
    stopsentence = (".", "!", "?",) 
    sentence = [] 
    sentencecount = 0 # reset the inner 'while' loop counter to zero 
    maxsentences = random.randrange(1,5) # random sentences per paragraph 

    while sentencecount < maxsentences: # start inner loop, until maxsentences is reached 
     newword = random.choice(table[(w1, w2)]) # random word from word table 
     if newword == stopword: sys.exit() 
     elif newword in stopsentence: 
      print ("%s%s" % (" ".join(sentence), newword), end=" ") 
      sentencecount += 1 # increment the sentence counter 
     else: 
      sentence.append(newword) 
     w1, w2 = w2, newword 
    print (paragraphsep) # newline space 
    paragraphs = paragraphs + 1 # increment the paragraph counter 


# EOF 

EDIT 02:

Dodany sentence = [] jak za odpowiedź poniżej w elif oświadczeniu. Na dowcip;

 elif newword in stopsentence: 
      print ("%s%s" % (" ".join(sentence), newword), end=" ") 
      sentence = [] # I have to be here to make the new sentence start as an empty list!!! 
      sentencecount += 1 # increment the sentence counter 

EDIT 03:

To jest ostatni iteracja tego skryptu. Dzięki żal za pomoc w posortowaniu tego. Mam nadzieję, że inni mogą się z tym dobrze bawić, wiem, że to zrobię. ;)

FYI: Istnieje jeden mały artefakt - istnieje dodatkowa przestrzeń na końcu akapitu, którą możesz wyczyścić, jeśli używasz tego skryptu. Ale, poza tym, doskonała implementacja generowania tekstu łańcucha Markowa.

### 
# usage: python markov_sentences.py <input.txt> output.txt 
# from: http://code.activestate.com/recipes/194364-the-markov-chain-algorithm/?in=lang-python 
### 

import random; 
import sys; 

stopword = "\n" # Since we split on whitespace, this can never be a word 
stopsentence = (".", "!", "?",) # Cause a "new sentence" if found at the end of a word 
sentencesep = "\n" #String used to seperate sentences 


# GENERATE TABLE 
w1 = stopword 
w2 = stopword 
table = {} 

for line in sys.stdin: 
    for word in line.split(): 
     if word[-1] in stopsentence: 
      table.setdefault((w1, w2), []).append(word[0:-1]) 
      w1, w2 = w2, word[0:-1] 
      word = word[-1] 
     table.setdefault((w1, w2), []).append(word) 
     w1, w2 = w2, word 
# Mark the end of the file 
table.setdefault((w1, w2), []).append(stopword) 

# GENERATE SENTENCE OUTPUT 
maxsentences = 20 

w1 = stopword 
w2 = stopword 
sentencecount = 0 
sentence = [] 
paragraphsep = "\n" 
count = random.randrange(1,5) 

while sentencecount < maxsentences: 
    newword = random.choice(table[(w1, w2)]) # random word from word table 
    if newword == stopword: sys.exit() 
    if newword in stopsentence: 
     print ("%s%s" % (" ".join(sentence), newword), end=" ") 
     sentence = [] 
     sentencecount += 1 # increment the sentence counter 
     count -= 1 
     if count == 0: 
      count = random.randrange(1,5) 
      print (paragraphsep) # newline space 
    else: 
     sentence.append(newword) 
    w1, w2 = w2, newword 


# EOF 

Odpowiedz

3

Trzeba skopiować

sentence = [] 

Powrót do klauzuli

elif newword in stopsentence: 

.

Więc

while paragraphs < maxparagraphs: # start outer loop, until maxparagraphs is reached 
    w1 = stopword 
    w2 = stopword 
    stopsentence = (".", "!", "?",) 
    sentence = [] 
    sentencecount = 0 # reset the inner 'while' loop counter to zero 
    maxsentences = random.randrange(1,5) # random sentences per paragraph 

    while sentencecount < maxsentences: # start inner loop, until maxsentences is reached 
     newword = random.choice(table[(w1, w2)]) # random word from word table 
     if newword == stopword: sys.exit() 
     elif newword in stopsentence: 
      print ("%s%s" % (" ".join(sentence), newword), end=" ") 
      sentence = [] # I have to be here to make the new sentence start as an empty list!!! 
      sentencecount += 1 # increment the sentence counter 
     else: 
      sentence.append(newword) 
     w1, w2 = w2, newword 
    print (paragraphsep) # newline space 
    paragraphs = paragraphs + 1 # increment the paragraph counter 

Edit

Oto rozwiązanie bez użycia zewnętrznej pętli.

""" 
    from: http://code.activestate.com/recipes/194364-the-markov-chain-algorithm/?in=lang-python 
""" 

import random; 
import sys; 

stopword = "\n" # Since we split on whitespace, this can never be a word 
stopsentence = (".", "!", "?",) # Cause a "new sentence" if found at the end of a word 
sentencesep = "\n" #String used to seperate sentences 


# GENERATE TABLE 
w1 = stopword 
w2 = stopword 
table = {} 

for line in sys.stdin: 
    for word in line.split(): 
     if word[-1] in stopsentence: 
      table.setdefault((w1, w2), []).append(word[0:-1]) 
      w1, w2 = w2, word[0:-1] 
      word = word[-1] 
     table.setdefault((w1, w2), []).append(word) 
     w1, w2 = w2, word 
# Mark the end of the file 
table.setdefault((w1, w2), []).append(stopword) 

# GENERATE SENTENCE OUTPUT 
maxsentences = 20 

w1 = stopword 
w2 = stopword 
sentencecount = 0 
sentence = [] 
paragraphsep == "\n\n" 
count = random.randrange(1,5) 

while sentencecount < maxsentences: 
    newword = random.choice(table[(w1, w2)]) 
    if newword == stopword: sys.exit() 
    if newword in stopsentence: 
     print ("%s%s" % (" ".join(sentence), newword), end=" ") 
     sentence = [] 
     sentencecount += 1 
     count -= 1 
     if count == 0: 
      count = random.randrange(1,5) 
      print (paragraphsep) 
    else: 
     sentence.append(newword) 
    w1, w2 = w2, newword 
+0

Ups! Tak, musiałem to w pewnym momencie wyciągnąć i zapomniałem włożyć to z powrotem. Dzięki za wgląd! To wystarczyło - prawie. Wydaje się, że pętla zdań ponownie używa tych samych słów początkowych dla każdego zdania. Jakieś pomysły na pomieszanie pierwszych słów, które wybiera do generowania zdań? –

+0

Dodałem osobne rozwiązanie, które nie wymaga zewnętrznej pętli. – grieve

+0

Nie mam zainstalowanego obecnie Pythona 3, więc może być konieczne zmodyfikowanie drugiego rozwiązania pod kątem składni. – grieve

1

Czy rozumiesz ten kod? Założę się, że możesz znaleźć kawałek, który drukuje zdanie, i zmienić go, by wydrukować kilka zdań razem, bez zwrotów. Możesz dodać kolejną pętlę while wokół bitów zdań, aby uzyskać wiele akapitów.

Składnia podpowiedź:

print 'hello' 
print 'there' 
hello 
there 

print 'hello', 
print 'there' 
hello there 

print 'hello', 
print 
print 'there' 

Chodzi o to, że przecinek na końcu instrukcji print uniemożliwia powrót na końcu linii, a pusty instrukcja print wypisuje zwrot.

+0

Tak, śledzę. Kłopot polega na tym, że wszystko, co wypróbowałem z instrukcją 'print', nie pomogło zebrać zdań w akapity (chyba że policzysz się z wycofaniem _wszystkich linii, tworząc jeden gigantyczny akapit). Pętla 'while' jest tym, o czym myślałem, ale nie byłem do końca pewien, jak zawinąć część zdania. Wszystko, co próbowałem, doprowadziło do różnych błędów, więc pomyślałem, że zapytam ekspertów. Jaki jest najlepszy sposób, aby to powiedzieć "wygenerować x (1-5 na przykład) ilość zdań, a następnie wstawić podział wiersza, a następnie powtarzać aż do osiągnięcia' maxsentences' "? –