public
Created

  • Download Gist
RegexTest.cs
C#
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Globalization;
using System.Text.RegularExpressions;
using System.Diagnostics;
 
namespace ConsoleApplication2
{
class Program
{
const string Test = "0x109237590827192938749123478234aefeadf1029481984901824290184";
const int Iterations = 1000000;
 
static void Main(string[] args)
{
Profile(IsHexRegexSlow, "Regex with no compiled/cached Regex");
Profile(IsHexRegexFast, "Regex with compiled/cached Regex");
Profile(IsHexFast, "Hand-written");
Console.ReadLine();
}
 
static void Profile(Func<string, bool> method, string description)
{
var sw = new Stopwatch();
// Warm up
method(Test);
sw.Start();
for (var i = 0; i < Iterations; i++)
method(Test);
sw.Stop();
Console.WriteLine("{0} took {1}ms", description, sw.ElapsedMilliseconds);
}
 
static bool IsHexRegexSlow(string value)
{
return Regex.IsMatch(value, "^0x(?:[0-9A-Fa-f]{2})+$");
}
 
static readonly Regex HexRegex = new Regex("^0x(?:[0-9A-Fa-f]{2})+$", RegexOptions.Compiled | RegexOptions.CultureInvariant);
static bool IsHexRegexFast(string value)
{
return HexRegex.IsMatch(value);
}
 
static bool IsHexFast(string value)
{
if (string.IsNullOrEmpty(value) || value.Length < 3)
return false;
 
const byte State_Zero = 0;
const byte State_X = 1;
const byte State_Value = 2;
 
var state = State_Zero;
 
for (var i = 0; i < value.Length; i++)
{
switch (value[i])
{
case '0':
{
// Can be used in either Value or Zero.
switch (state)
{
case State_Zero: state = State_X; break;
case State_X: return false;
case State_Value: break;
}
}
break;
case 'X': case 'x':
{
// Only valid in X.
switch (state)
{
case State_Zero: return false;
case State_X: state = State_Value; break;
case State_Value: return false;
}
}
break;
case '1': case '2': case '3': case '4': case '5': case '6': case '7': case '8': case '9':
case 'A': case 'B': case 'C': case 'D': case 'E': case 'F':
case 'a': case 'b': case 'c': case 'd': case 'e': case 'f':
{
// Only valid in Value.
switch (state)
{
case State_Zero: return false;
case State_X: return false;
case State_Value: break;
}
}
break;
default: return false;
}
}
 
return state == State_Value;
}
}
}

Please sign in to comment on this gist.

Something went wrong with that request. Please try again.