ИЗМЕНИТЬ 2:
Подтверждено, что мои проблемы с производительностью были вызваны вызовом статической функции классу StringExtensions. После удаления метод IndexOf действительно самый быстрый способ выполнить это.
Что такое самый быстрый, нечувствительный к регистру, способ увидеть, содержит ли строка другую строку в С#? Я вижу принятое решение для сообщения здесь в нечувствительном к регистру 'Contains (string)', но я сделал предварительный бенчмаркинг, и кажется, что использование этого метода приводит к порядкам амплитуда медленнее вызывает более крупные строки ( > 100 символов) всякий раз, когда тестовая строка не может быть найдена.
Вот методы, которые я знаю:
IndexOf:
public static bool Contains(this string source, string toCheck, StringComparison comp)
{
if (string.IsNullOrEmpty(toCheck) || string.IsNullOrEmpty(source))
return false;
return source.IndexOf(toCheck, comp) >= 0;
}
ToUpper:
source.ToUpper().Contains(toCheck.ToUpper());
Regex:
bool contains = Regex.Match("StRiNG to search", "string", RegexOptions.IgnoreCase).Success;
Итак, мой вопрос в том, что действительно самый быстрый способ в среднем и почему так?
EDIT:
Вот мое простое тестовое приложение, которое я использовал, чтобы подчеркнуть разницу в производительности. Используя это, я вижу 16 мс для ToLower(), 18 мс для ToUpper и 140 мс для StringExtensions.Contains():
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Globalization;
namespace ScratchConsole
{
class Program
{
static void Main(string[] args)
{
string input = "";
while (input != "exit")
{
RunTest();
input = Console.ReadLine();
}
}
static void RunTest()
{
List<string> s = new List<string>();
string containsString = "1";
bool found;
DateTime now;
for (int i = 0; i < 50000; i++)
{
s.Add("AAAAAAAAAAAAAAAA AAAAAAAAAAAA");
}
now = DateTime.Now;
foreach (string st in s)
{
found = st.ToLower().Contains(containsString);
}
Console.WriteLine("ToLower(): " + (DateTime.Now - now).TotalMilliseconds);
now = DateTime.Now;
foreach (string st in s)
{
found = st.ToUpper().Contains(containsString);
}
Console.WriteLine("ToUpper(): " + (DateTime.Now - now).TotalMilliseconds);
now = DateTime.Now;
foreach (string st in s)
{
found = StringExtensions.Contains(st, containsString, StringComparison.OrdinalIgnoreCase);
}
Console.WriteLine("StringExtensions.Contains(): " + (DateTime.Now - now).TotalMilliseconds);
}
}
public static class StringExtensions
{
public static bool Contains(this string source, string toCheck, StringComparison comp)
{
return source.IndexOf(toCheck, comp) >= 0;
}
}
}