有没有比查找字符串的字符串数组更快的方法?

时间:2014-06-16 18:02:14

标签: c# arrays visual-studio-2010 list

目前我这样做:

        List<int> ID = new List<int>();
        int a = 0;
        string[] findWordHere = ...
        string[] findOtherWordHere = ...
        string word = "this";
        string otherWord = "that";

        foreach (string word in findWordHere)
        {
            foreach (string otherWord in findOtherWordHere)
            {
                if (word == otherWord)
                {
                    ID.Add(a + 1);
                }
            }
            a++;
        }

这非常耗时。有没有更好的方法来做到这一点,比如linq?

3 个答案:

答案 0 :(得分:3)

是的,有。在第一个循环之前将findOtherWordHere中的所有项添加到HashSet<string>,并将其用于查找,如下所示:

ISet<string> lookup = new HashSet<string>(findOtherWordHere);
foreach (string word in findWordHere)
{
    if (lookup.Contains(word))
    {
        ID.Add(a + 1);
    }
    a++;
}

这与findWordHerefindOtherWordHere长度的总和成比例,因为HashSet<string>是以线性时间建立的,并提供恒定时间查找功能。

另一方面,您的原始方法与findWordHerefindOtherWordHere长度的产品成比例地运行,因为最坏的情况是执行内循环到在外循环的每次迭代中完成。

答案 1 :(得分:2)

您可以使用HashSet<string>

var set = new HashSet<string>(findOtherWordHere);
var IDs = findWordHere
            .Select((w,i) => new {w,i})
            .Where(p => set.Contains(p.w))
            .Select(p => p.i)
            .ToList();

这提供了另一个列表中包含的单词的索引,没有循环且具有合理的性能。

答案 2 :(得分:0)

如果您不需要数组,可以使用StringComparison方法:

            List<int> ID = new List<int>();

            int a = 0;

            string root = "that";
            string root2 = "that";

            bool result = root.Equals(root2, StringComparison.Ordinal);


            if (result)
            {
               ID.Add(a + 1);
            }

或者如果你想忽略大小写使用OrdinalIgnoreCase请记住顺序是比较两个字符串的最快方法:

        List<int> ID = new List<int>();

        int a = 0;

        string root = "that";
        string root2 = "that";

        bool result = root.Equals(root2, StringComparison.OrdinalIgnoreCase);


        if (result)
        {
           ID.Add(a + 1);
        }