Python - подстановочные знаки, генерирующие гласные - PullRequest
0 голосов
/ 29 сентября 2018

Народ,

Изучая себя на Python через открытую программу курса, я получил задание на стене.

Обычно пользователь вводит слово с * в месте для гласного.,Пример: 'd * g' для dig, dog или dug.

Написанная мною программа заменит * на значение из объекта: vowels = 'aeiou', а затем просмотрит список слов и увидит,есть совпадениеПример: d * g -> * dag: нет совпадений, deg: нет совпадений, dig: match;конец поиска.

for char_vow in VOWELS:
  wildcard_word=word.replace('*',char_vow)
  print(wildcard_word)
  if wildcard_word in word_list:
      word=wildcard_word
      break

Это прекрасно работало, когда был один '*', но моя программа не может обрабатывать два или более.Например, если пользователь введет d ** th для смерти, код будет проверять только daath, deeth, diith, dooth, duuth и затем возвращать false.

Итак, я подумал, что рекурсия может быть ответоми выписал:

def wildcard_replacement(word):
    wildcard_word=""
    if word.find('*')==-1:
        return word
    else:
        for char_vow in VOWELS:
              wildcard_word=word.replace('*',char_vow,1)
              print(wildcard_word)
              if wildcard_word in word_list:
                  word=wildcard_word
                  break
              elif wildcard_word.find('*')!=-1:
                  return wildcard_replacement(wildcard_word)
        return wildcard_replacement(wildcard_word)

    print(wildcard_replacement(word))

Эта программа искала: daath, daeth, daith, daoth, dauth, затем остановилась.Что задним числом имеет смысл.Больше нет *.Но я хочу, чтобы первый гласный теперь переворачивался от a к и e, а затем продолжал цикл замены для второго подстановочного знака.Я застрял ...

Есть предложения?

Ответы [ 3 ]

0 голосов
/ 29 сентября 2018

Рекурсивная функция - хорошая идея

def expand_vowels(word):

, если в word нет диких символов, мы выдаем неизменное слово и используем оператор return, чтобы сигнализировать, что рекурсия закончена

    if '*' not in word: yield word ; return

если мы здесь, то есть хотя бы один '*' в word

    for new_word in (word.replace('*', vw, 1) for v in 'aeiou'):
        for new2_word in expand_vowels(new_word): yield new2_word

Все это легко собрать вместе с помощью нескольких простых тестов

$ cat vow.py
def expand_vowels(word):
    if '*' not in word: yield word ; return
    for new_word in (word.replace('*', v, 1) for v in 'aeiou'):
        for new2_word in expand_vowels(new_word): yield new2_word

for w in ('a', 'a*', 'a**'):
    print(list(expand_vowels(w)))

good = ['aei', 'bwe']

for wild in ('a**', 'b**'):
    for word in expand_vowels(wild):
        if word in good:
            print(word, 'is in the good words')
            break
    else:
        print(wild, 'doesn\'t generate a good word')
$ python vow.py
['a']
['aa', 'ae', 'ai', 'ao', 'au']
['aaa', 'aae', 'aai', 'aao', 'aau', 'aea', 'aee', 'aei', 'aeo', 'aeu', 'aia', 'aie', 'aii', 'aio', 'aiu', 'aoa', 'aoe', 'aoi', 'aoo', 'aou', 'aua', 'aue', 'aui', 'auo', 'auu']
aei is in the good words
b** doesn't generate a good word
$
0 голосов
/ 01 октября 2018

Что вы могли бы сделать здесь, используя itertools product , вы можете указать комбинации гласных, необходимые в примере death, это будет 2, тогда мы можем установить repeat = 2 и получить всеДвухбуквенные комбинации гласных, тогда мы могли бы использовать str.replace для замены '**' комбинациями гласных, пока мы не получим совпадение в wordbank

from itertools import product

vowels = 'aeiou'
wordbank = ['death']
word = 'd**th'
x = word.count('*')

l = [''.join(i) for i in [*product(vowels, repeat = x)]]
print(l)

for i in l:
    guess = word.replace('**', i)
    if guess in wordbank:
        print(guess)
        break
 death
0 голосов
/ 29 сентября 2018

Это потому, что вы делаете return в ветви elif (под вами for).Таким образом, по сути, вы никогда не перебираете все гласные на своем верхнем уровне, так как после того, как вы остановили * и заменили его, больше не осталось ...

Предложения (поскольку, похоже, вы на самом деле этого не делаетехотите получить ответ " code "):

  1. Проверьте, принадлежит ли слово вашему словарю (word_list) в предельном регистре (т. е. когда нет *);
  2. Всегда отправлять временный результат (после того, как вы заменили одну из *) в функцию;
  3. Если вы хотите break на первом найденном действительном слове, я быпроверить результат вызова wildcard_replacement вместо чего-то другого (вы фактически делаете проверку на wildcard_word вместо возвращаемого значения);
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...