Warning: file_get_contents(/data/phpspider/zhask/data//catemap/1/php/283.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
.net 为什么';t StringBuilder是否有IndexOf方法?_.net_Stringbuilder - Fatal编程技术网

.net 为什么';t StringBuilder是否有IndexOf方法?

.net 为什么';t StringBuilder是否有IndexOf方法?,.net,stringbuilder,.net,Stringbuilder,我知道我可以调用ToString().IndexOf(…),但我不想创建额外的字符串。我知道我可以手动编写搜索例程。我只是想知道为什么框架中还没有这样一个例程。不幸的是,为String实现的许多方法本来可以为StringBuilder实现,但没有实现。考虑使用扩展方法来添加你关心的东西。 < p>调用 toStrug()/ < StringBuilder > 不会产生额外的对象,令人困惑。在内部,StringBuilder存储字符串对象,以提高性能;调用ToString()只会返回该对象。我知道

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

不幸的是,为String实现的许多方法本来可以为StringBuilder实现,但没有实现。考虑使用扩展方法来添加你关心的东西。

< p>调用<代码> toStrug()/<代码> < StringBuilder > <代码>不会产生额外的对象,令人困惑。在内部,
StringBuilder
存储字符串对象,以提高性能;调用
ToString()
只会返回该对象。

我知道这是一个老问题,但是我已经编写了一个扩展方法,在
StringBuilder
上执行
索引。它在下面。我希望它能帮助任何人找到这个问题,无论是从谷歌搜索还是搜索StackOverflow

//
///返回StringBuilder中内容开头的索引
///         
///要查找的字符串
///起始索引。
///如果设置为true,它将忽略大小写
/// 
公共静态int IndexOf(此StringBuilder sb、字符串值、int startIndex、bool ignoreCase)
{            
整数指数;
int length=value.length;
int maxSearchLength=(sb.Length-Length)+1;
如果(忽略案例)
{
对于(int i=startIndex;i
丹尼斯,很好的解决方案。谢谢 我建议稍微优化一下:

公共静态int IndexOf(
这是一个很好的例子,
字符串值,
int startIndex,
布尔格诺尔案)
{
int len=值。长度;
int max=(sb.Length-len)+1;
变量v1=(忽略案例)
?value.ToLower():值;
变量func1=(ignoreCase)
新函数((x,y)=>char.ToLower(x)==y)
:新函数((x,y)=>x==y);
对于(int i1=startIndex;i1
如果在问题的上下文中要求stringbuilder修改自身,则这是不正确的。创建新字符串时,内部缓冲区的易变性不会暴露于托管代码中。@ShuggyCoUk:我的评论有点油嘴滑舌。我已经删除了它。为了澄清前面的评论,调用ToString不会有太多开销。但是在调用它之后,对StringBuilder的下一次修改将产生复制开销。(这是一个有效的优化,因为ToString通常是StringBuilder最后一件事。)因此,类字符串方法的高效实现不能使用ToString,这就排除了原始海报问题的简单解决方案。这个答案是误导性的,因为它表明
ToString
方法只是返回一个已经可用的字符串。事实并非如此。有一些奇怪的代码使用
wstrcpy
(查看了ILSpy.NET4中的反编译代码)从这个stringbuilder创建一个新字符串。来源:这显然不是禁止操作。我猜这也适用于角色比较:公平的呼唤;请随意编辑以上帖子。对不起,我错了。实际上,微软已经优化了ToUpperInvariant(),而不是ToUpper()。在这种情况下,我们不能默认提供ToUpperInvariant(),因为它可能导致某些语言(如Turkish)中的错误比较。所以,在这方面,你的代码是绝对正确的,错了也没关系。感谢您再次光临并发表评论:+1:@Sergey:应该使用
ToUpperInvariant
,因为它正确地大写了Turkish-I,而
ToLower
ToLowerInvariant
不正确?这很难理解。
/// <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;
}