在字符串中放置随机字符,除非是某个特定单词

2 投票
6 回答
2274 浏览
提问于 2025-04-17 10:44

比如,我有这样一个字符串:

Hello how are you today, [name]?

我想知道怎么在随机选择的单词之间随机放置字符,但不包括[name]。我已经有了这段代码,但我希望能有更好的方法来实现这个。

string = 'Hello how are you today, [name]?'
characters = 'qwertyuioplkjhgfdsazxcvbnm,. '
arr = string.rsplit(" ")

for i in range(0, len(arr)):
    x = arr[i]
    if x == '[name]':
        continue
    if (random.randint(0,2)==1) :
        rnd=random.randint(1,len(x)-2)
        tmp1 = random.randint(0,len(characters))
        rndCharacter = characters[tmp1:tmp1+1]
        x = x[0:rnd] + rndCharacter + x[rnd+1:]
        arr[i] = x

" ".join(arr)

> Hellio how are yoy todsy, [name]?"

虽然这段代码是用另一个随机字符替换了原来的字符,但我想知道有没有办法让它随机在某个字符的前面或后面放置一个随机字符?

基本上,我就是想模拟一个打字错误生成器。

谢谢

这是我目前代码的更新:

string = 'Hey how are you doing, [name]?'
characters = 'aeiou'
arr = string.rsplit(" ")
for i in range(0, len(arr)):
    x = arr[i]
    if x == '[name]': continue
    if len(x) > 3:
        if random.random() > 0.7:
            rnd = random.randint(0,len(x)-1)
            rndCharacter = random.choice(characters)
            if random.random() > 0.7:
                x = x[0:rnd] + rndCharacter + x[rnd+1:]
            else:
                x = x[:rnd] + rndCharacter + x[rnd:]
            arr[i] = x
    else:
        if random.random() > 0.7:
            rnd = random.randint(0,len(x)-1)
            rndCharacter = random.choice(characters)
            x = x[:rnd] + rndCharacter + x[rnd:]
            arr[i] = x
print " ".join(arr)

> Hey houw are you doiang, [name]?

更新:

也许这是我对代码的最后一次更新,希望这能在未来某个时候帮助到别人。

def misspeller(word):
    typos = { 'a': 'aqwedcxzs',
              'b': 'bgfv nh',
              'c': 'cdx vf',
              'd': 'desxcfr',
              'e': 'e3wsdfr4',
              'f': 'fredcvgt',
              'g': 'gtrfvbhyt',
              'h': 'hytgbnju',
              'i': 'i8ujko9',
              'j': 'juyhnmki',
              'k': 'kiujm,lo',
              'l': 'loik,.;p',
              'm': 'mkjn ,',
              'n': 'nhb mjh',
              'o': 'o9ikl;p0',
              'p': 'p0ol;[-',
              'q': 'q1asw2',
              'r': 'r4edft5',
              's': 'swazxde',
              't': 't5rfgy6',
              'u': 'u7yhji8',
              'v': 'vfc bg',
              'w': 'w2qasde3',
              'x': 'xszcd',
              'y': 'y6tghu7',
              'z': 'zaZxs',
              ' ': ' bvcnm',
              '"': '"{:?}',
              '\'': '[;/\']',
              ':': ':PL>?"{',
              '<': '<LKM >',
              '>': '>:L<?:',
              ';': ';pl,.;[',
              '[': '[-p;\']=',
              ']': '=[\'',
              '{': '{[_P:"}+',
              '}': '}=[\']=',
              '|': '|\]\'',
              '.': '.l,/;',
              ',': ',lkm.'
            }

    index = random.randint(1,len(word)-1)
    letter = list(word[:index])[-1].lower()
    try:
        if random.random() <= 0.5:
            return word[:index] + random.choice(list(typos[letter])) + word[index:]
        else:
            return word[:index-1] + random.choice(list(typos[letter])) + word[index:]
    except KeyError:
        return word

def generate(self, s, n, safe_name):
    misspelled_s = ''
    misspelled_list = []
    for item in s.split(' '):
        if n:
            if safe_name in item:
                misspelled_list.append(item)
            else:
                r = random.randint(0,1)
                if r == 1 and len(re.sub('[^A-Za-z0-9]+', '', item)) > 3:
                    misspelled_list.append(misspeller(item))
                    n -= 1
                else:
                    misspelled_list.append(item)
        else:
            misspelled_list.append(item)
    return ' '.join(misspelled_list)

6 个回答

1

我觉得@sgallen的回答是可行的,但我有一些建议(针对你之前的代码,以及未来的代码)。

for i in range(0, len(arr)):
    x = arr[i]

# is the same as

for i,x in enumerate(arr):

else:
    if random...:

# to

elif random...:

string当作变量名用其实不太好。原因是,Python里有一个叫string的模块。这个模块可能会对你有帮助,特别是里面的字符串常量。你可以考虑用inpdata或者sentence这样的名字。

# For example

>>> import string
>>> string.lowercase
'abcdefghijklmnopqrstuvwxyz'

顺便说一下,如果有人发现上面的内容有错误,请留言。谢谢。

2

如果你想在某个字母前面或后面添加一个字母,而不是替换掉原来的字母,你只需要调整一下你的切片索引,确保它们不会跳过一个字母。也就是说,使用

x = x[:rnd] + rndCharacter + x[rnd:]

这样的话,新添加的字符就会插入到中间,而不是替换掉原来的字符。

另外,你可以用 rndCharacter = random.choice(characters) 来代替使用 tmp1,这样做也可以。

2
import random

def misspeller(word):
    characters = 'qwertyuioplkjhgfdsazxcvbnm,. '
    rand_word_position = random.randint(-1,len(word))
    rand_characters_position = random.randint(0,len(characters)-1)

    if rand_word_position == -1:
        misspelled_word = characters[rand_characters_position] + word 
    elif rand_word_position == len(word):
        misspelled_word = word + characters[rand_characters_position] 
    else:
        misspelled_word = list(word)
        misspelled_word[rand_word_position] = characters[rand_characters_position]
        misspelled_word = ''.join(misspelled_word)        
    return misspelled_word

s = 'Hello how are you today, [name]?'
misspelled_s = ''
misspelled_list = []
for item in s.split(' '):
    if '[name]' in item:
        misspelled_list.append(item)
    else:
        misspelled_list.append(misspeller(item))
misspelled_s = ' '.join(misspelled_list)
print misspelled_s

我从 misspelled_s 得到的例子是:

'Hellk howg ars youf poday, [name]?'
'Heylo how arer y,u todab, [name]?'
'Hrllo hfw  are zyou totay, [name]?'

编辑过,修正了一些错误和遗漏。

编辑 2 如果你不想让每个单词都受到影响,可以这样修改循环:

for item in s.split(' '):
    n = random.randint(0,1)
    if '[name]' in item:
        misspelled_list.append(item)
    elif n == 1:
        misspelled_list.append(misspeller(item))
    else:
        misspelled_list.append(item)

你可以通过改变 n 的生成方式来调整一个单词被修改的概率,比如 n = random.randint(0,10)

撰写回答