为什么StringBuilder没有IndexOf方法?

时间:2009-08-31 23:55:29

标签: .net stringbuilder

我知道我可以调用ToString()。IndexOf(...),但我不想创建额外的字符串。我知道我可以手动编写搜索例程。我只是想知道为什么框架中不存在这样的例程。

4 个答案:

答案 0 :(得分:43)

我知道这是一个老问题,但是我编写了一个在IndexOf上执行StringBuilder的扩展方法。它在下面。我希望通过 Google 搜索或搜索 StackOverflow 来帮助找到此问题的任何人。

/// <summary>
/// Returns the index of the start of the contents in a StringBuilder
/// </summary>        
/// <param name="value">The string to find</param>
/// <param name="startIndex">The starting index.</param>
/// <param name="ignoreCase">if set to <c>true</c> it will ignore case</param>
/// <returns></returns>
public static int IndexOf(this StringBuilder sb, string value, int startIndex, bool ignoreCase)
{            
    int index;
    int length = value.Length;
    int maxSearchLength = (sb.Length - length) + 1;

    if (ignoreCase)
    {
        for (int i = startIndex; i < maxSearchLength; ++i)
        {
            if (Char.ToLower(sb[i]) == Char.ToLower(value[0]))
            {
                index = 1;
                while ((index < length) && (Char.ToLower(sb[i + index]) == Char.ToLower(value[index])))
                    ++index;

                if (index == length)
                    return i;
            }
        }

        return -1;
    }

    for (int i = startIndex; i < maxSearchLength; ++i)
    {
        if (sb[i] == value[0])
        {
            index = 1;
            while ((index < length) && (sb[i + index] == value[index]))
                ++index;

            if (index == length)
                return i;
        }
    }

    return -1;
}

答案 1 :(得分:6)

不幸的是,为String实现的许多方法都可以为StringBuilder实现,但是没有完成。考虑使用扩展方法添加您关心的内容。

答案 2 :(得分:0)

ToString()上调用StringBuilder不会造成额外的对象,令人困惑。在内部,StringBuilder存储一个String对象,以提高性能;调用ToString()只会返回该对象。

答案 3 :(得分:-1)

丹尼斯,很好的解决方案。谢谢。 我建议对其进行一些优化:

public static int IndexOf(
    this StringBuilder sb,
    string value,
    int startIndex,
    bool ignoreCase)
{
    int len = value.Length;
    int max = (sb.Length - len) + 1;
    var v1 = (ignoreCase)
        ? value.ToLower() : value;
    var func1 = (ignoreCase)
        ? new Func<char, char, bool>((x, y) => char.ToLower(x) == y)
        : new Func<char, char, bool>((x, y) => x == y);
    for (int i1 = startIndex; i1 < max; ++i1)
        if (func1(sb[i1], v1[0]))
        {
            int i2 = 1;
            while ((i2 < len) && func1(sb[i1 + i2], v1[i2]))
                ++i2;
            if (i2 == len)
                return i1;
        }
    return -1;
}