在python中使用正则表达式捕获表情

2024-09-19 20:33:01 发布

您现在位置:Python中文网/ 问答频道 /正文

我希望有一个正则表达式模式来匹配smileys“:”,“:(”。它还应该捕获重复的smileys,如“:)”,“:):(,但过滤掉无效语法,如“:(”。

我随身带着这个,但它是匹配的:

bool( re.match("(:\()",str) ) 

我可能遗漏了一些显而易见的东西,我想为这个看似简单的任务提供一些帮助。


Tags: rematch模式语法boolstrsmileys遗漏
3条回答

尝试(?::|;|=)(?:-)?(?:\)|\(|D|P)。还没有广泛的测试,但似乎匹配正确的,而不是更多。。。

In [15]: import re

In [16]: s = "Just: to :)) =) test :(:-(( ():: :):) :(:( :P ;)!"

In [17]: re.findall(r'(?::|;|=)(?:-)?(?:\)|\(|D|P)',s)
Out[17]: [':)', '=)', ':(', ':-(', ':)', ':)', ':(', ':(', ':P', ';)']

我想它终于“点击”了,正是你在这里问的。看看下面:

import re

smiley_pattern = '^(:\(|:\))+$' # matches only the smileys ":)" and ":("

def test_match(s):
    print 'Value: %s; Result: %s' % (
        s,
        'Matches!' if re.match(smiley_pattern, s) else 'Doesn\'t match.'
    )

should_match = [
    ':)',   # Single smile
    ':(',   # Single frown
    ':):)', # Two smiles
    ':(:(', # Two frowns
    ':):(', # Mix of a smile and a frown
]
should_not_match = [
    '',         # Empty string
    ':(foo',    # Extraneous characters appended
    'foo:(',    # Extraneous characters prepended
    ':( :(',    # Space between frowns
    ':( (',     # Extraneous characters and space appended
    ':(('       # Extraneous duplicate of final character appended
]

print('The following should all match:')
for x in should_match: test_match(x);

print('')   # Newline for output clarity

print('The following should all not match:')
for x in should_not_match: test_match(x);

原始代码的问题在于regex是错误的:(:\()。让我们把它分解。

外括号是一个“分组”。如果要进行字符串替换,则需要引用它们,并用于同时对字符组应用正则表达式运算符。所以,你真的是在说:

  • (开始一个组
    • :\(。。。做正则表达式的事情。。。
  • “)”结束组

:不是regex保留字符,所以它只是一个冒号。\是,它的意思是“以下字符是文本字符,而不是正则表达式运算符”。这被称为“转义序列”。完全解析为英语,你的regex说

  • (开始一个组
    • :结肠特征
    • \(左括号字符
  • )结束组

我使用的regex稍微复杂一些,但还不错。让我们把它分解成:^(:\(|:\))+$

^$分别表示“行的开始”和“行的结束”。现在我们有。。。

  • ^行首
    • (:\(|:\))+。。。做正则表达式的事情。。。
  • $行尾

。。。所以它只匹配组成整行的内容,而不是简单地出现在字符串的中间。

我们知道()表示一个分组。+表示“其中一个”。现在我们有:

  • ^行首
  • (启动组
    • :\(|:\)。。。做正则表达式的事情。。。
  • )结束组
  • +匹配一个或多个
  • $行尾

最后是|(管道)操作符。意思是“或”。因此,应用上面关于转义字符的知识,我们可以完成转换:

  • ^行首
  • (启动组
    • :结肠特征
    • \(左括号字符
  • |
    • :结肠特征
    • \)右括号字符
  • )结束组
  • +匹配一个或多个
  • $行尾

我希望这能有帮助。如果没有,请让我知道,我很乐意修改我的答复。

可能是这样的:

re.match('[:;][)(](?![)(])', str)

相关问题 更多 >