如何查看字符串是否仅包含 python 中的子字符串
How to see if a string ONLY contains a substring in python
我需要能够查看一个字符串是否只包含一个子字符串或一个字母,而不包含其他内容。
说我想检测World
这将包含子字符串,但它也有不同顺序的不同字母
"Hello World"
这不包含任何不同的字母或顺序,只是子串 3 次
"WorldWorldWorld"
如果我想检测_
这不会通过
"Hello_World"
但这会
"___"
我该怎么做?
使用正则表达式。
if re.match("(?:World)+", s):
仅当 s
包含字符串 World
的一次或多次重复时才会成功。
这是正则表达式的作业,re.match()
。
import re
re.match(r"(?:World)+", "World")
re.match(r"(?:World)+", "Hello World")
re.match(r"(?:World)+", "WorldWorldWorld")
您可以使用正则表达式,使用 re.escape
生成匹配目标连续出现一次或多次的模式(使用 ^
和 $
表示开始和字符串的末尾)以及 re.match
来确定它是否匹配所需的模式:
import re
target = "World"
data = "World" * 3
pattern = f"^({re.escape(target)})+$"
re.match(pattern, data) is not None
这输出:
True
方法一:
如果没有正则表达式(regexes),可以简单地使用sets。首先,将有问题的字符串s
拆分为与子字符串substr
长度相同的子字符串。从这些子字符串中创建一个集合 s_set
。如果该集合只有 1 个元素,并且该元素在 substr
中,则打印 True
,否则 False
.
strs = ["WorldWorldWorld", "Hello World"]
substr = "World"
len_substr = len(substr)
for s in strs:
s_set = set(s[i:(i + len_substr)] for i in range(0, len(s), len_substr))
print(len(s_set) == 1 and substr in s_set)
# True
# False
方法二:
如果速度很重要,那么对于非常长的字符串,在找到第一个 non-matching 子字符串后立即停止是有意义的,如以下解决方案所示:
for s in strs:
only_substr = True
for i in range(0, len(s), len_substr):
cur_substr = s[i:(i + len_substr)]
if cur_substr != substr:
only_substr = False
break
print(only_substr)
# True
# False
不需要正则表达式。根据 str.count
计算 non-overlapping 次的事实
len(target) * data.count(target) == len(data)
这里简单的字符串方法比正则表达式快 400-800%:
>>> import re
>>> target = "World"
>>> data = "World" * 3
>>> pattern = f"^({re.escape(target)})+$"
>>> %timeit len(target) * data.count(target) == len(data)
115 ns ± 0.352 ns per loop (mean ± std. dev. of 7 runs, 10,000,000 loops each)
>>> %timeit re.match(pattern, data) is not None
456 ns ± 2.88 ns per loop (mean ± std. dev. of 7 runs, 1,000,000 loops each)
>>> %timeit bool(data.replace(target, '')) # str.replace is faster again
51.7 ns ± 0.269 ns per loop (mean ± std. dev. of 7 runs, 10,000,000 loops each)
我需要能够查看一个字符串是否只包含一个子字符串或一个字母,而不包含其他内容。
说我想检测World
这将包含子字符串,但它也有不同顺序的不同字母
"Hello World"
这不包含任何不同的字母或顺序,只是子串 3 次
"WorldWorldWorld"
如果我想检测_
这不会通过
"Hello_World"
但这会
"___"
我该怎么做?
使用正则表达式。
if re.match("(?:World)+", s):
仅当 s
包含字符串 World
的一次或多次重复时才会成功。
这是正则表达式的作业,re.match()
。
import re
re.match(r"(?:World)+", "World")
re.match(r"(?:World)+", "Hello World")
re.match(r"(?:World)+", "WorldWorldWorld")
您可以使用正则表达式,使用 re.escape
生成匹配目标连续出现一次或多次的模式(使用 ^
和 $
表示开始和字符串的末尾)以及 re.match
来确定它是否匹配所需的模式:
import re
target = "World"
data = "World" * 3
pattern = f"^({re.escape(target)})+$"
re.match(pattern, data) is not None
这输出:
True
方法一:
如果没有正则表达式(regexes),可以简单地使用sets。首先,将有问题的字符串s
拆分为与子字符串substr
长度相同的子字符串。从这些子字符串中创建一个集合 s_set
。如果该集合只有 1 个元素,并且该元素在 substr
中,则打印 True
,否则 False
.
strs = ["WorldWorldWorld", "Hello World"]
substr = "World"
len_substr = len(substr)
for s in strs:
s_set = set(s[i:(i + len_substr)] for i in range(0, len(s), len_substr))
print(len(s_set) == 1 and substr in s_set)
# True
# False
方法二:
如果速度很重要,那么对于非常长的字符串,在找到第一个 non-matching 子字符串后立即停止是有意义的,如以下解决方案所示:
for s in strs:
only_substr = True
for i in range(0, len(s), len_substr):
cur_substr = s[i:(i + len_substr)]
if cur_substr != substr:
only_substr = False
break
print(only_substr)
# True
# False
不需要正则表达式。根据 str.count
计算 non-overlapping 次的事实
len(target) * data.count(target) == len(data)
这里简单的字符串方法比正则表达式快 400-800%:
>>> import re
>>> target = "World"
>>> data = "World" * 3
>>> pattern = f"^({re.escape(target)})+$"
>>> %timeit len(target) * data.count(target) == len(data)
115 ns ± 0.352 ns per loop (mean ± std. dev. of 7 runs, 10,000,000 loops each)
>>> %timeit re.match(pattern, data) is not None
456 ns ± 2.88 ns per loop (mean ± std. dev. of 7 runs, 1,000,000 loops each)
>>> %timeit bool(data.replace(target, '')) # str.replace is faster again
51.7 ns ± 0.269 ns per loop (mean ± std. dev. of 7 runs, 10,000,000 loops each)