下面的代码检查用户是否输入了语法正确的网址。正则表达式代码来自 Regular expressions in C: examples?
printf("Enter the website URL:\n");
fgets(str, 100, stdin);
if (!strcmp(str, "\n")) {
printf("Empty URL ");
exit(2);
}
regex_t regex;
int reti;
char msgbuf[100];
/* Compile regular expression */
reti = regcomp(®ex, "[a-zA-Z0-9\\-\\.]+\\.[a-zA-Z]{2,3}(/\\S*)?$", 0);
if (reti) {
fprintf(stderr, "Could not compile regex\n");
exit(3);
}
/* Execute regular expression */
reti = regexec(®ex, str, 0, NULL, 0);
if (!reti) {
puts("Match");
} else if (reti == REG_NOMATCH) { //This else if always executes.
puts("No match");
exit(4);
} else {
regerror(reti, ®ex, msgbuf, sizeof (msgbuf));
fprintf(stderr, "Regex match failed: %s\n", msgbuf);
exit(5);
}
/* Free compiled regular expression if you want to use the regex_t again */
regfree(®ex);
然而,即使输入的网址正确,正则表达式总是失败。我知道正则表达式是正确的,但由于某种原因它在“执行正则表达式”部分失败。即使用户输入语法正确的 URL,else if 也始终会执行。
else if 总是执行的原因可能是什么?
最佳答案
您的模式无效有效!
请注意,POSIX 定义了两种类型的正则表达式:基本 (BRE) 和扩展 (ERE)(请参阅 Wikipedia )。由于您想使用“扩展”风格,请将 REG_EXTENDED
标志传递给 regcomp()
。
以下是您的模式存在的(一些?)问题:
[a-zA-Z0-9\\-\\.]+\\.[a-zA-Z]{2,3}(/\\S*)
- 在方括号 (
[]
) 内,不需要转义特殊字符。事实上,您无法转义它们,并且[a-zA-Z0-9\-\.]
将匹配反斜杠,但不匹配连字符,因为\-\
被解释范围从\
到\
。如果要匹配连字符,请将其放在字符列表中的第一个或最后一个:[a-zA-Z0-9.-]
- POSIX 不支持 Perl 风格的字符类
\S
。请改用[^[:space:]]
。 - 量词
{}
需要用BRE写成\{\}
- 仅 ERE 支持
+
和?
量词
总而言之,将对 regcomp()
的调用替换为以下代码:
reti = regcomp(®ex, "[a-zA-Z0-9.-]+\\.[a-zA-Z]{2,3}(/[^[:space:]]*)?$", REG_EXTENDED);
关于c 正则表达式代码不起作用?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/9681162/