Хорошо, здесь есть ответ, который показывает вам, как узнать, имеет ли эта строка длину 32 символа, и каждый символ представляет собой либо цифру, либо строчную букву «a», либо строчную букву «f» с регулярным выражением, а другой - показывает, как это сделать с помощью простого Func, который сканирует эти символы в строке. Они оба являются хорошими ответами и технически верны, но в заголовке вашего вопроса вы явно указываете «GUID», который открывает новую банку с червями.
GUID может принимать несколько различных строковых представлений, и вы можете встретить любое из них. Вам нужно справиться со всем этим? Вам нужно будет разместить строки, которые начинаются и заканчиваются фигурными скобками ('{' и '}') или круглыми скобками? А как насчет тире ('-')? Согласно MSDN , создание нового GUID с
string s = ...;
Guid g = new Guid(s);
Позволяет использовать строки в следующих формах
32 смежных цифр:
ддддддддддддддддддддддд
-или-
Группы из 8, 4, 4, 4 и 12 цифр
с дефисами между группами.
весь GUID может быть при желании
в соответствующих скобках или скобках:
ддддддд-дддд-дддд-дддд-дддддддддд
-или-
{DDDDDDDDDDDD-DDDDDDDD-DDDDDDDDDDDD}
-или-
(DDDDDDDDDDDD-DDDDDDDD-DDDDDDDDDDDD)
-или-
Группы из 8, 4 и 4 цифр и
подмножество из восьми групп из 2 цифр,
с каждой группой с префиксом «0x» или
«0X» и разделены запятыми.
весь GUID, а также подмножество
заключены в соответствующие фигурные скобки: {0xdddddddd, 0xdddd, 0xdddd, {0xdd, 0xdd, 0xdd, 0xdd, 0xdd, 0xdd, 0xdd, 0xdd}}
Вам нужно разобраться со всеми этими случаями? Кроме того, подумайте, является ли использование регулярного выражения действительно лучшим вариантом. Как уже отмечали некоторые люди, регулярные выражения могут вводить в заблуждение некоторых разработчиков, и цель не всегда ясна. Кроме того, в некоторых случаях регулярное выражение может быть медленным .
Я провел быстрый тест производительности на трех разных способах определения, является ли строка на самом деле строковым представлением GUID:
- Regex
- Проверка всех символов в строке
- Создание нового экземпляра Guid с заданной строкой (если Guid может быть создан, то строка является допустимым строковым представлением)
Вот код:
[Test]
public void Test_IsRegex_Performance()
{
Action withRegexMatch = () =>
{
Regex regex = new Regex("^[0-9a-f]{32}$");
Guid g = new Guid();
string s = g.ToString();
regex.IsMatch(s);
};
Action withCharCheck = () =>
{
Guid g = new Guid();
string s = g.ToString();
Func<char, bool> charValid = c => (c >= '0' && c <= '9') || (c >= 'a' && c <= 'f');
bool isValid = s.Length == 32 && s.All(charValid);
};
Action withNewGuid = () =>
{
Guid g = new Guid();
string s = g.ToString();
try
{
Guid g2 = new Guid(s);
// if no exception is thrown, this is a valid string
// representation
}
catch
{
// if an exception was thrown, this is an invalid
// string representation
}
};
const int times = 100000;
Console.WriteLine("Regex: {0}", TimedTask(withRegexMatch, times));
Console.WriteLine("Checking chars: {0}", TimedTask(withCharCheck, times));
Console.WriteLine("New Guid: {0}", TimedTask(withNewGuid, times));
Assert.Fail();
}
private static TimeSpan TimedTask(Action action, int times)
{
Stopwatch timer = new Stopwatch();
timer.Start();
for (int i = 0; i < times; i++)
{
action();
}
timer.Stop();
return timer.Elapsed;
}
И результаты миллиона итераций на моей машине:
Regex: 00:00:10.1786901
Checking chars: 00:00:00.2504520
New Guid: 00:00:01.3129005
Итак, решение регулярных выражений медленное. Спросите себя, действительно ли вам нужно здесь регулярное выражение. Обратите внимание, что вы, вероятно, можете добиться некоторой дополнительной производительности, только объявив регулярное выражение один раз и повторно его применив, но я думаю, что смысл в этом случае в том, что вы можете добиться большего успеха, посмотрев на что вы пытаетесь выполнить, в отличие от как .
Надеюсь, это поможет.