5

この最初の文字列があります。

'bananaappleorangestrawberryapplepear'

また、文字列を持つタプルがあります。

('apple', 'plepe', 'leoran', 'lemon')

最初の文字列と文字列のタプルから次のようになる関数が必要です。

'bananaxxxxxxxxxgestrawberryxxxxxxxar'

私は、すべての単語の最初の文字列で単語を見つけてから、すべての最初の文字列で単語を置き換えて文字ごとにループすることによって、それを実行する方法を知っています。

しかし、それはあまり効率的で醜いものではありません。itertoolsなどを使用して、機能的な方法でこれをよりエレガントに行う方法があるはずだと思います。これを効率的に実行できるPythonライブラリをご存知の場合は、お知らせください。

更新:Justin Peelは、最初の質問で説明しなかったケースを指摘しました。単語が「aaa」で、「aaaaaa」が最初の文字列に含まれている場合、出力は「xxxxxx」のようになります。

4

6 に答える 6

3
import re

words = ('apple', 'plepe', 'leoran', 'lemon')
s = 'bananaappleorangestrawberryapplepear'

x = set()

for w in words:
    for m in re.finditer(w, s):
        i = m.start()
        for j in range(i, i+len(w)):
            x.add(j)

result = ''.join(('x' if i in x else s[i]) for i in range(len(s)))
print result

生成:

bananaxxxxxxxxxgestrawberryxxxxxxxar
于 2010-11-13T18:36:27.903 に答える
1

別の答えがあります。文字をxに置き換えるより速い方法があるかもしれませんが、これはすでにかなり速いので、私はそれが必要であるとは思いません。

import re

def do_xs(s,pats):
    pat = re.compile('('+'|'.join(pats)+')')

    sout = list(s)
    i = 0
    match = pat.search(s)
    while match:
        span = match.span()
        sout[span[0]:span[1]] = ['x']*(span[1]-span[0])
        i = span[0]+1
        match = pat.search(s,i)
    return ''.join(sout)

txt = 'bananaappleorangestrawberryapplepear'
pats = ('apple', 'plepe', 'leoran', 'lemon')
print do_xs(txt,pats)

基本的に、どの入力パターンにも一致する正規表現パターンを作成します。次に、最新の一致の開始位置の1から検索を再開し続けます。ただし、入力パターンの1つが別の入力パターンのプレフィックスである場合は、問題が発生する可能性があります。

于 2010-11-13T19:19:25.450 に答える
1

stdlibやその他のインポートなしでの作業に制限されていると仮定します。

s1 = 'bananaappleorangestrawberryapplepear'
t = ('apple', 'plepe', 'leoran', 'lemon')
s2 = s1

solution = 'bananaxxxxxxxxxgestrawberryxxxxxxxar'

for word in t:
    if word not in s1: continue
    index = -1 # Start at -1 so our index search starts at 0
    for iteration in range(s1.count(word)):
        index = s1.find(word, index+1)
        length = len(word)
        before = s2[:index]
        after = s2[index+length:]
        s2 = before + 'x'*length + after

print s2 == solution
于 2010-11-13T19:42:56.643 に答える
1
>>> string_ = 'bananaappleorangestrawberryapplepear'
>>> words = ('apple', 'plepe', 'leoran', 'lemon')
>>> xes = [(string_.find(w), len(w)) for w in words]
>>> xes
[(6, 5), (29, 5), (9, 6), (-1, 5)]
>>> for index, len_ in xes:
...   if index == -1: continue
...   string_ = string_.replace(string_[index:index+len_], 'x'*len_)
...
>>> string_
'bananaxxxxxxxxxgestrawberryxxxxxxxar'
>>>

確かにもっと効果的な方法がありますが、時期尚早の最適化はすべての悪の根源です。

于 2010-11-13T22:10:50.263 に答える
0
a = ('apple', 'plepe', 'leoran', 'lemon')
b = 'bananaappleorangestrawberryapplepear'

for fruit in a:
    if a in b:
        b = b.replace(fruit, numberofx's)

あなたが今しなければならない唯一のことは、彼が置き換えるXの数を決定することです。

于 2010-11-13T18:10:43.470 に答える
0
def mask_words(s, words):
    mask = [False] * len(s)
    for word in words:
        pos = 0
        while True:
            idx = s.find(word, pos)
            if idx == -1:
                break

            length = len(word)
            for i in xrange(idx, idx+length):
                mask[i] = True
            pos = idx+length

    # Sanity check:
    assert len(mask) == len(s)

    result = []
    for masked, c in zip(mask, s):
        result.append('x' if masked else c)

    return "".join(result)
于 2010-11-13T18:30:06.560 に答える