正则表达式匹配路径

Posted

技术标签:

【中文标题】正则表达式匹配路径【英文标题】:Regex to match path 【发布时间】:2020-09-30 16:58:01 【问题描述】:

我试图验证用户输入的字符串是否正确。

不应以 assets/ 开头 不应以 / 结尾 不应以任何文件扩展名结尾,例如 .html 或 .php 或 .jpg 不应包含点 .

我正在尝试使用下面的正则表达式,但它无法正常工作。

^([a-z]:)*(\/*(\.*[a-z0-9]+\/)*(\.*[a-z0-9]+))

我的测试用例

有效路径

样本/你好/图像 sample/hello_vid/user/data test/123/user_live/images

路径无效

assets/sample/hello/images sample/hello_vid/user/data/ test/123/user_live/images/index.html hii/sk.123/data ok/bye/last.exe

【问题讨论】:

你需要它只是一个正则表达式还是可以使用 System.IO.Path 的方法? “它不应该包含一个点”这足以排除 .jpg、.pdf 等 路径可以包含比[a-z0-9]+ 更多的字符。考虑使用\w+ 【参考方案1】:

另一种“可读”方法;)

public static bool IsValidPath(this string path)

    if (string.IsNullOrEmpty(path)) return false;
    if (path.StartsWith("assets/")) return false;
    if (path.EndsWith("/")) return false;
    if (path.Contains(".")) return false;

    return true;


// Usage
var value = "sample/hello/images";
if (value.IsValidPath())

    // use the value...

【讨论】:

【参考方案2】:

如果您还想匹配下划线,您可以将其添加到字符类中。为防止在开始时匹配 assets/,您可以使用否定前瞻。

^(?!assets/)[a-z0-9_]+(?:/[a-z0-9_]+)+$
^ 字符串开始 (?!assets/) 断言右边不是assets/ [a-z0-9_]+ 重复 1 次以上列出的任何内容,包括下划线 (?:/[a-z0-9_]+)+ 重复 1+ 次 / 和 1+ 次任何列出的 $ 字符串结束

Regex demo

或者你可以使用\w 代替字符类

^(?!assets/)\w+(?:/\w+)+$

【讨论】:

为什么这个答案被否决了?请至少提及相同的原因。如果您在答案中提供有效的缺陷,我相信回答者可以纠正这些问题。我没有看到任何顺便说一句。【参考方案3】:

这适用于您的测试用例。

Regex explained:
^(?!assets/) # It should not start with assets/
[^\.]+       # It should not contain dot (file extensions contain a dot)
(?<!/)$      # It should not end with /

Regex in one line:
^(?!assets/)[^\.]+(?<!/)$

【讨论】:

【参考方案4】:

您可以尝试以下正则表达式来实现您的目的:

^(?!assets\/)[^.]*?$(?<!\/\r?$)

上述正则表达式的解释:

^, $ - 分别代表行的开始和结束。

(?!assets\/) - 表示与以assets\ 开头的测试字符串不匹配的否定前瞻。

[^.]*? - 匹配除. 之外的所有惰性。这种情况下也会覆盖文件扩展名,因此无需再次检查。

(?&lt;!\/\r?$) - 如果测试字符串包含 \ 作为最后一个字符,则表示不匹配测试字符串。

你可以在here.找到上述正则表达式的demo

在 C# 中的实现

using System;
using System.Text.RegularExpressions;

public class Example

    public static void Main()
    
        string pattern = @"^(?!assets\/)[^.]*?$(?<!\/\r?$)";
        string input = @"sample/hello/images
sample/hello_vid/user/data
test/123/user_live/images
assets/sample/hello/images
sample/hello_vid/user/data/
test/123/user_live/images/index.html
hii/sk.123/data
ok/bye/last.exe";
        RegexOptions options = RegexOptions.Multiline;
        
        foreach (Match m in Regex.Matches(input, pattern, options))
        
            Console.WriteLine(m.Value);
        
    

您可以在here.找到上述代码的示例运行

【讨论】:

【参考方案5】:

以下正则表达式应该适用于您提到的场景:

^((?!(assets\/))(?! )([a-zA-Z0-9_ ]+(?<! )\/(?! ))+[a-zA-Z0-9_ ]+)$

除了问题中的场景外,我还处理了一个文件夹名称不以空格开头或结尾的问题。

【讨论】:

以上是关于正则表达式匹配路径的主要内容,如果未能解决你的问题,请参考以下文章

php正则匹配图片路径

Java 正则表达式:如何匹配 URL 路径?

求一个正则表达式:校验url和磁盘路径。

Nginx学习笔记04URL匹配规则和实际路径

正则表达式匹配除特定路径之外的所有https URL

调整 Django URL 中的正则表达式以匹配文件路径