Regex 与 Tryparse 哪个性能最好

发布于 2024-11-02 09:19:21 字数 139 浏览 5 评论 0原文

在我的 ASP.net 项目中,我需要验证用户输入的一些基本数据类型。数据类型包括数字、小数、日期时间等。

就性能而言,我应该采取的最佳方法是什么?是通过Regex.IsMatch()还是通过TryParse()来完成?

提前致谢。

In my ASP.net project I need to validate some basic data types for user inputs. The data types are like numeric, decimal, datetime etc.

What is the best approach that I should have taken in terms of performance? Is it to do it by Regex.IsMatch() or by TryParse()?

Thanks in advance.

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(4

你的心境我的脸 2024-11-09 09:19:21

TryParseRegex.IsMatch 用于两个根本不同的事情。 Regex.IsMatch 告诉您相关字符串是否与某些特定模式匹配。它返回是/否答案。 TryParse 实际上会在可能的情况下转换该值,并告诉您是否成功。

除非您在构建正则表达式时非常小心,否则当 TryParse 返回时,Regex.IsMatch 可能会返回 true 。例如,考虑解析字节的简单情况。使用 TryParse,您可以:

byte b;
bool isGood = byte.TryParse(myString, out b);

如果 myString 中的值在 0 到 255 之间,TryParse 将返回 true

现在,让我们尝试使用 Regex.IsMatch。让我们看看,这个正则表达式应该是什么?我们不能只说 @"\d+" 甚至 @\d{1,3}"。指定格式变得非常困难。你必须处理前导 0、前导和尾随空格,并允许 255 但不允许 256

这仅适用于解析 3 位数字。重新解析一个intlong

正则表达式非常适合确定形式,但在确定时却很糟糕。我们的标准数据类型都有限制,确定其值是确定数字是否有效的一部分,

您最好尽可能使用 TryParse ,哪怕只是为了省去尝试的麻烦。提出一个可靠的正则表达式来进行验证是可能的。 (我几乎可以肯定)任何本机类型的特定 TryParse 都会比等效的正则表达式执行得更快。

上面说过,我在这个答案上花费的时间可能比您更多 。网页将在其整个生命周期中花费执行 TryParseRegex.IsMatch 的时间。与您的网站所做的其他所有事情相比,执行这些事情的时间是如此之少,您花在思考问题上的任何时间都被浪费了。

如果可以的话,请使用 TryParse,因为它更容易。否则使用正则表达式。

TryParse and Regex.IsMatch are used for two fundamentally different things. Regex.IsMatch tells you if the string in question matches some particular pattern. It returns a yes/no answer. TryParse actually converts the value if possible, and tells you whether it succeeded.

Unless you're very careful in crafting the regular expression, Regex.IsMatch can return true when TryParse will return false. For example, consider the simple case of parsing a byte. With TryParse you have:

byte b;
bool isGood = byte.TryParse(myString, out b);

If the value in myString is between 0 and 255, TryParse will return true.

Now, let's try with Regex.IsMatch. Let's see, what should that regular expression be? We can't just say @"\d+" or even @\d{1,3}". Specifying the format becomes a very difficult job. You have to handle leading 0s, leading and trailing white space, and allow 255 but not 256.

And that's just for parsing a 3-digit number. The rules get even more complicated when you're parsing an int or long.

Regular expressions are great for determining form. They suck when it comes to determining value. Since our standard data types all have limits, determining its value is part of figuring out whether or not the number is valid.

You're better off using TryParse whenever possible, if only to save yourself the headache of trying to come up with a reliable regular expression that will do the validation. It's likely (I'd say almost certain) that a particular TryParse for any of the native types will execute faster than the equivalent regular expression.

The above said, I've probably spent more time on this answer than your Web page will spend executing your TryParse or Regex.IsMatch--total throughout its entire life. The time to execute these things is so small in the context of everything else your Web site is doing, any time you spend pondering the problem is wasted.

Use TryParse if you can, because it's easier. Otherwise use Regex.

酒儿 2024-11-09 09:19:21

正如其他人所说,回答这个问题的最好方法是衡量它;)

    static void Main(string[] args)
    {

        List<double> meansFailedTryParse = new List<double>();
        List<double> meansFailedRegEx = new List<double>();
        List<double> meansSuccessTryParse = new List<double>();
        List<double> meansSuccessRegEx = new List<double>();


        for (int i = 0; i < 1000; i++)
        {


            string input = "123abc";

            int res;
            bool res2;
            var sw = Stopwatch.StartNew();
            res2 = Int32.TryParse(input, out res);
            sw.Stop();
            meansFailedTryParse.Add(sw.Elapsed.TotalMilliseconds);
            //Console.WriteLine("Result of " + res2 + " try parse :" + sw.Elapsed.TotalMilliseconds);

            sw = Stopwatch.StartNew();
            res2 = Regex.IsMatch(input, @"^[0-9]*$");
            sw.Stop();
            meansFailedRegEx.Add(sw.Elapsed.TotalMilliseconds);
            //Console.WriteLine("Result of " + res2 + "  Regex.IsMatch :" + sw.Elapsed.TotalMilliseconds);

            input = "123";
            sw = Stopwatch.StartNew();
            res2 = Int32.TryParse(input, out res);
            sw.Stop();
            meansSuccessTryParse.Add(sw.Elapsed.TotalMilliseconds);
            //Console.WriteLine("Result of " + res2 + " try parse :" + sw.Elapsed.TotalMilliseconds);


            sw = Stopwatch.StartNew();
            res2 = Regex.IsMatch(input, @"^[0-9]*$");
            sw.Stop();
            meansSuccessRegEx.Add(sw.Elapsed.TotalMilliseconds);
            //Console.WriteLine("Result of " + res2 + "  Regex.IsMatch :" + sw.Elapsed.TotalMilliseconds);
        }

        Console.WriteLine("Failed TryParse mean execution time     " + meansFailedTryParse.Average());
        Console.WriteLine("Failed Regex mean execution time        " + meansFailedRegEx.Average());

        Console.WriteLine("successful TryParse mean execution time " + meansSuccessTryParse.Average());
        Console.WriteLine("successful Regex mean execution time    " + meansSuccessRegEx.Average());
    }
}

As other would say, the best way to answer that is to measure it ;)

    static void Main(string[] args)
    {

        List<double> meansFailedTryParse = new List<double>();
        List<double> meansFailedRegEx = new List<double>();
        List<double> meansSuccessTryParse = new List<double>();
        List<double> meansSuccessRegEx = new List<double>();


        for (int i = 0; i < 1000; i++)
        {


            string input = "123abc";

            int res;
            bool res2;
            var sw = Stopwatch.StartNew();
            res2 = Int32.TryParse(input, out res);
            sw.Stop();
            meansFailedTryParse.Add(sw.Elapsed.TotalMilliseconds);
            //Console.WriteLine("Result of " + res2 + " try parse :" + sw.Elapsed.TotalMilliseconds);

            sw = Stopwatch.StartNew();
            res2 = Regex.IsMatch(input, @"^[0-9]*$");
            sw.Stop();
            meansFailedRegEx.Add(sw.Elapsed.TotalMilliseconds);
            //Console.WriteLine("Result of " + res2 + "  Regex.IsMatch :" + sw.Elapsed.TotalMilliseconds);

            input = "123";
            sw = Stopwatch.StartNew();
            res2 = Int32.TryParse(input, out res);
            sw.Stop();
            meansSuccessTryParse.Add(sw.Elapsed.TotalMilliseconds);
            //Console.WriteLine("Result of " + res2 + " try parse :" + sw.Elapsed.TotalMilliseconds);


            sw = Stopwatch.StartNew();
            res2 = Regex.IsMatch(input, @"^[0-9]*$");
            sw.Stop();
            meansSuccessRegEx.Add(sw.Elapsed.TotalMilliseconds);
            //Console.WriteLine("Result of " + res2 + "  Regex.IsMatch :" + sw.Elapsed.TotalMilliseconds);
        }

        Console.WriteLine("Failed TryParse mean execution time     " + meansFailedTryParse.Average());
        Console.WriteLine("Failed Regex mean execution time        " + meansFailedRegEx.Average());

        Console.WriteLine("successful TryParse mean execution time " + meansSuccessTryParse.Average());
        Console.WriteLine("successful Regex mean execution time    " + meansSuccessRegEx.Average());
    }
}
GRAY°灰色天空 2024-11-09 09:19:21

不要试图让正则表达式做所有事情。

有时,一个简单的正则表达式就可以完成 90% 的任务,但为了让它完成您需要的一切,复杂性会增加十倍甚至更多。

然后我经常发现最简单的解决方案是使用正则表达式检查表单,然后依赖良好的旧代码进行值检查。

以日期为例,使用正则表达式检查日期格式是否匹配,然后使用捕获组检查各个值的值。

Don't try to make regexes do everything.

Sometimes a simple regex will get you 90% of the way and to make it do everything you need the complexity grows ten times or more.

Then I often find that the simplest solution is to use the regex to check the form and then rely on good old code for the value checking.

Take a date for example, use a regex to check for a match on a date format and then use capturing groups to check the values of the individual values.

凝望流年 2024-11-09 09:19:21

我猜想 TryParse 更快,但更重要的是,它更具表现力。

当您考虑正在使用的每种数据类型的所有有效值时,正则表达式可能会变得非常难看。例如,对于 DateTime,您必须确保月份在 1 到 12 之间,并且日期在该特定月份的有效范围内。

I'd guess TryParse is quicker, but more importantly, it's more expressive.

The regular expressions can get pretty ugly when you consider all the valid values for each data type you're using. For example, with DateTime you have to ensure the month is between 1 and 12, and that the day is within the valid range for that particular month.

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文