Python正则表达式没有返回预期值

时间:2017-10-31 22:49:59

标签: python regex string

问题:

如果说一句话,你需要判断其中大写字母的使用是否正确。

当下列情况之一成立时,我们将单词中大写字母的用法定义为正确:

这个单词中的所有字母都是大写字母,如“USA”。 这个单词中的所有字母都不是大写字母,如“leetcode”。 如果它有多个字母,只有这个词中的第一个字母是大写字母,如“Google”。 否则,我们定义该单词不以正确的方式使用大写字母。

我的解决方案(使用正则表达式库)

导入重新

def detectCapitalUse(word):

    pattern = r'[A-Z]*|[A-Z]?[a-z]*'
    r = re.search(pattern, word)
    print r.group()

模式的前半部分[A-Z]*应匹配所有大写字母或第二部分[A-Z]?[a-z]*应匹配任何以一个大写字母开头且其余为小写或与单词匹配的单词只有小写字母。

当我写下面的测试用例时,我得到了意想不到的答案

detectCapitalUse("Flag") Expected: Flag Actual Value: F

detectCapitalUse("flag") Expected: flag Actual Value: Empty string

我做错了什么?

4 个答案:

答案 0 :(得分:0)

您可能想要更像r'[A-Z]?[a-z]+|[A-Z]+'

的内容

您的模式无法按预期工作的原因可以从re模块文档收集:

  

扫描目标字符串时,从左到右尝试由'|'分隔的RE。当一个模式完全匹配时,接受该分支。

因此[A-Z]*分支在一个大写字符上立即匹配,并且该匹配是返回的内容。

答案 1 :(得分:0)

您遇到的问题与此正则表达式[A-Z]*启动匹配的事实有关,然后在完成Flag之类的案例之前停止。尝试通过要求[A-Z]匹配至少两个或更多字母来解决此问题。试试这个正则表达式:

[A-Z]{2,}|[A-Z]?[a-z]*

演示:https://regex101.com/r/H2ExoN/1/

答案 2 :(得分:0)

首先考虑第一个要求:所有字母都是大写字母。回想一下,*匹配零次或多次,因此可以很好地匹配空字符串。这解释了你上面的第二个意外情况。另请注意,re.search()匹配字符串中的任何位置,因此您需要从头部和尾部排除非大写字母。一种方法是匹配模式的开始和结束,并设置最小匹配计数以排除空字符串:

^[A-Z]{1,}$

(请注意,这也将匹配单个大写字母。)

同样的考虑因素适用于您的第二种情况。所以你的组合模式是:

^[A-Z]{1,}$|^[A-Z]?[a-z]{1,}$

或者:

^([A-Z]{1,}|[A-Z]?[a-z]{1,})$

答案 3 :(得分:0)

让事情变得简单:您可以通过要求它匹配整个字符串来修复您的解决方案,这就是您的意思:r"^([A-Z]*|[A-Z]?[a-z]*)$"将按预期工作。