基准测试 .Net 正则表达式选项 - 或者从右到左做什么

本文关键字:从右到左 什么 或者 Net 正则表达式 选项 基准测试 | 更新日期: 2023-09-27 18:34:18

>我创建了一个演示应用程序来测试一些正则表达式的性能。我的第三个测试使用选项从右到左。

似乎它大大加快了这个过程!为什么?它有什么作用?

这是我的测试应用程序:

using System;
using System.Collections.Generic;
using System.Diagnostics;
using System.Linq;
using System.Text;
using System.Text.RegularExpressions;
using System.Threading.Tasks;
namespace ConsoleApplication1
{
    class Program
    {
        private const string IsRequestForDirectoryWithoutTrailingSlashRegex = @"^(?#Path:)(.*/)?(?#LastPart:)(?<!'.asmx|'.aspx/)([^./?#]+?)(?#QueryString:)('?.*?)(?#Anchor:)?(#.*)?$";
        private static string[] Tests = new string[] {
            "http://localhost/manager/page.aspx",
            "http://localhost/manager/",
            "http://localhost/manager",
            "http://localhost/manager/?param=value",
            "http://localhost/manager/dir?param=value"
        };
        static void Main(string[] args)
        {
            Test1();
            Test2();
            Test3();
            Test4();
            Console.WriteLine();
            Console.ReadLine();
        }
        public static void Test1()
        {
            Regex regex = new Regex(IsRequestForDirectoryWithoutTrailingSlashRegex);
            DoWork("1", regex);
        }
        public static void Test2()
        {
            Regex regex = new Regex(IsRequestForDirectoryWithoutTrailingSlashRegex, RegexOptions.Compiled);
            DoWork("2", regex);
        }
        public static void Test3()
        {
            Regex regex = new Regex(IsRequestForDirectoryWithoutTrailingSlashRegex, RegexOptions.Compiled | RegexOptions.RightToLeft);
            DoWork("3", regex);
        }
        public static void Test4()
        {
            Regex regex = new Regex(IsRequestForDirectoryWithoutTrailingSlashRegex, RegexOptions.Compiled | RegexOptions.RightToLeft | RegexOptions.IgnoreCase);
            DoWork("4", regex);
        }
        static void DoWork(string name, Regex regex)
        {
            Stopwatch sp = new Stopwatch();
            sp.Start();
            for (int i = 0; i < 100000; i++)
            {
                foreach (string s in Tests)
                {
                    regex.IsMatch(s);
                }
            }
            foreach (string s in Tests)
            {
                Console.WriteLine(":" + s + ":" + regex.IsMatch(s).ToString());
            }
            sp.Stop();
            Console.WriteLine("Test " + name + ": " + sp.ElapsedTicks);
        }
    }
}

基准测试 .Net 正则表达式选项 - 或者从右到左做什么

当您尝试匹配您希望在输入字符串末尾找到的模式时,RegexOptions.RightToLeft非常有用,因为正如其文档所说: 搜索从输入字符串中的最后一个字符开始从右到左从左到右,但正则表达式本身仍然从左

到右应用。

您的正则表达式似乎正在寻找目录路径的尾部斜杠,因此这种情况似乎符合描述。

虽然你的表达式正在寻找一个尾部斜杠,但这两个锚点(^$(的存在使我的推理是错误的,因为正则表达式无论从哪里开始,都只能以一种可能的方式匹配。

我将继续寻找这背后的实际原因,但现在我将保持我的答案不变。

另一方面,表达式的.*/部分紧跟在表达式开头的(?#Path:)部分之后会消耗整个输入字符串,然后每次都会递归返回以查找最后一个/,因此当进一步开始搜索时,可能不会有很多回溯。