Php 预匹配排除字符串
从10000行数据中,我必须得到所有不包含以“en”或“it”或“de”等开头的单词的行,它们的a-z和a-z长度从2到5,也有“-”(减号)和“;” 我试过了,但没用Php 预匹配排除字符串,php,regex,preg-match,Php,Regex,Preg Match,从10000行数据中,我必须得到所有不包含以“en”或“it”或“de”等开头的单词的行,它们的a-z和a-z长度从2到5,也有“-”(减号)和“;” 我试过了,但没用 !preg_match("/\b(it|en|de|es|fr|ru)[a-zA-Z-;]{2,5}/", $value) (对我来说)这是不匹配的所有行都有以它开头的单词,en等由2到5个字符组成,在这5个字符中还可以包含“-”或“;” 这将返回带有“it”的行,我需要排除这些行 编辑:我需要匹配以这两个字符开头的每个单词
!preg_match("/\b(it|en|de|es|fr|ru)[a-zA-Z-;]{2,5}/", $value)
(对我来说)这是不匹配的所有行都有以它开头的单词,en等由2到5个字符组成,在这5个字符中还可以包含“-”或“;”
这将返回带有“it”的行,我需要排除这些行
编辑:我需要匹配以这两个字符开头的每个单词(it、en或de),并且可以在行中的任何位置
要匹配的示例(不包含以“en”、“de”等开头的单词)
示例不匹配(它确实包含以“en”开头的单词)
您正在寻找的魔法字符是插入符号:
^
:
!preg_match("/^(it|en|de|es|fr|ru)[a-zA-Z-;]{2,5}/", $value)
除此之外,看起来还不错。您正在寻找的魔法角色是插入符号:
^
:
!preg_match("/^(it|en|de|es|fr|ru)[a-zA-Z-;]{2,5}/", $value)
除此之外,看起来不错。您可以使用:
此处,(?!…)
断言,如果不实际匹配包含模式,则包含模式从当前位置开始不得存在匹配。您可以使用:
此处,
(?!…)
断言,如果不实际匹配包含模式,则从当前位置开始的包含模式不得匹配。最简单的方法是首先将数据拆分为单独的行,然后逐个检查:
$lines = explode("\n", $data); // I'm making an assumption here, discussed below.
foreach ($lines as $line)
{
if (!preg_match('/\b(?=it|en|de|es|fr|ru)[a-z;-]{2,5}/i', $line))
{
// line doesn't contain a word beginning with en, de, etc.
}
}
您对\b
元字符的使用应该正确<代码>\b如果第一个字符是单词字符,则在字符串开头匹配
我正在使用((?=)
)检查单词的前两个字符是否是您要查找的语言代码。这避免了@Aasmund Eldhuset在中指出的问题。换句话说,正则表达式引擎查找以要排除的语言代码开头的单词,但匹配结果由PHP逻辑反转,因此包含这些单词的任何行都将被忽略
我假设您的数据被一个
\n
(换行符)字符分割成几行。它可能被\r
或\n\r
拆分。如果您不知道使用了哪些换行符,可以使用代替,即:
最简单的方法是首先将数据拆分为单独的行,然后逐个检查:
$lines = explode("\n", $data); // I'm making an assumption here, discussed below.
foreach ($lines as $line)
{
if (!preg_match('/\b(?=it|en|de|es|fr|ru)[a-z;-]{2,5}/i', $line))
{
// line doesn't contain a word beginning with en, de, etc.
}
}
您对\b
元字符的使用应该正确<代码>\b如果第一个字符是单词字符,则在字符串开头匹配
我正在使用((?=)
)检查单词的前两个字符是否是您要查找的语言代码。这避免了@Aasmund Eldhuset在中指出的问题。换句话说,正则表达式引擎查找以要排除的语言代码开头的单词,但匹配结果由PHP逻辑反转,因此包含这些单词的任何行都将被忽略
我假设您的数据被一个
\n
(换行符)字符分割成几行。它可能被\r
或\n\r
拆分。如果您不知道使用了哪些换行符,可以使用代替,即:
据我所知,您的正则表达式匹配的字符串以一个国家代码开头,总长度为4-7,而不是2-5。So
en代码>不匹配,因为它只包含三个符号。{2,5}
仅适用于其最左边的表达式,因此您的正则表达式读取“一个以它/en/de等开头并以两到五个字母/破折号/分号继续的单词”。请尝试\b(it | en | de | es | fr | ru)[A-zA-Z-]{0,3}
您可能还希望明确分号是最后一个字符,也可能更具体地说明ISO语言代码的结构(我假设这些字符串是):\b(it | en | de | es | fr | ru)([a-zA-Z]{2})\b
。在这里,我们说“一个以/en/de等开头的单词可能会以破折号和两个字母继续,而(不管它是否有破折号和两个字母)可能会以分号继续。在这个单词结束之前,不允许有任何其他内容。”据我所知,您的正则表达式匹配以某个国家/地区代码开头且总长度为4-7而不是2-5的字符串。Soen代码>不匹配,因为它只包含三个符号。{2,5}
仅适用于其最左边的表达式,因此您的正则表达式读取“一个以它/en/de等开头并以两到五个字母/破折号/分号继续的单词”。请尝试\b(it | en | de | es | fr | ru)[A-zA-Z-]{0,3}
您可能还希望明确分号是最后一个字符,也可能更具体地说明ISO语言代码的结构(我假设这些字符串是):\b(it | en | de | es | fr | ru)([a-zA-Z]{2})\b
。在这里,我们说“一个以/en/de等开头的单词可能会以破折号和两个字母继续,并且(不管它是否有破折号和两个字母)可能会以分号继续。在该单词结束之前,不允许有任何其他内容。”你能给我们看一些你正在匹配的数据吗?你能给我们看一些你正在匹配的数据吗?不太清楚。插入符号匹配行首,但不匹配单词的开头(当然,行首的单词除外)\b
匹配单词边界(也可能不是单词的开头,因为单词边界只是指\W
中的字符和\W
中的字符之间的位置)。这会返回零行,但是有些行的开头是这样的,他说他想忽略以l开头的行
$lines = explode("\n", $data); // I'm making an assumption here, discussed below.
foreach ($lines as $line)
{
if (!preg_match('/\b(?=it|en|de|es|fr|ru)[a-z;-]{2,5}/i', $line))
{
// line doesn't contain a word beginning with en, de, etc.
}
}
$lines = preg_split('/\n|\n?\r/', $data);