`
iamzhongyong
  • 浏览: 805564 次
  • 性别: Icon_minigender_1
  • 来自: 杭州
社区版块
存档分类
最新评论

StringBuilder的toString方法

    博客分类:
  • java
 
阅读更多

前几天发布应用出现了点问题,排查过程中同事发在群里一篇文章,仔细看了一下,还是挺有意思的,于是自己模拟了一下场景,

原文在这里,一次简单致命的错误:http://www.blogjava.net/xylz/archive/2012/03/15/371966.html

在频繁的进行字符串的操作增加的时候,我们会优先考虑使用StringBuilderStringBuffer,其中StringBuffer是线程安全的。有个小地方需要慎重,就是toString()方法。

 

先看这段代码://读取文件,然后在文件的末尾追加一些特殊字符然后换行

	public static void main(String[] args) throws Exception {
		BufferedReader reader = new BufferedReader(
                       new FileReader("E:\\java_tools\\hatrix1.28\\hatrix.log"));
		StringBuilder sb = new StringBuilder();
		String str = null;
		while((str=reader.readLine())!=null){
			if(StringUtils.isNotEmpty(sb.toString())){
				sb.append("$$$$$$$$\r");
			}
			sb.append(str);
		}
		System.out.println(sb.toString());
	}

 

 

上面标红的这里,在小应用或者数据量不大的情况下完全没有问题,但是在数据量大,并且并发多的时候,就会出现问题。

 

在Stringbuilder的代码中看toString()的代码如下

 

  public String toString() {
        // Create a copy, don't share the array
	return new String(value, 0, count);
    }

 

 每次调用toString方法,会重新new一个String出来。

 

 

在java.lang.String的代码中,看最后一行,value并不是直接指向的,而是通过系统拷贝函数进行的内存操作

 public String(char value[], int offset, int count) {
        if (offset < 0) {
            throw new StringIndexOutOfBoundsException(offset);
        }
        if (count < 0) {
            throw new StringIndexOutOfBoundsException(count);
        }
        // Note: offset or count might be near -1>>>1.
        if (offset > value.length - count) {
            throw new StringIndexOutOfBoundsException(offset + count);
        }
        this.offset = 0;
        this.count = count;
        this.value = Arrays.copyOfRange(value, offset, offset+count);
    }
 

java.util.Arrays中关于数组拷贝

 

  public static char[] copyOfRange(char[] original, int from, int to) {
        int newLength = to - from;
        if (newLength < 0)
            throw new IllegalArgumentException(from + " > " + to);
        char[] copy = new char[newLength];
        System.arraycopy(original, from, copy, 0,  Math.min(original.length - from, newLength));
        return copy;
    }

 

 

那为啥会通过内存拷贝的形式来进行toString呢,原因在于StringBuilder内部有两个核心的属性,这两个记录了String中的内容,是字符数组的形式。

这时候对于字符数组操作,通过内存拷贝是最快的方式了。

 

  /**
     * The value is used for character storage.
     */
    char value[];

    /** 
     * The count is the number of characters used.
     */
    int count; 

 

上述代码中,CPU会一直忙于进行内存的分配工作,会导致机器的load过高

 

解决办法:

 

用StringBuilder类中的length来判断是否有数值,这样就避免了无谓的内存操作。

分享到:
评论

相关推荐

    StringBuilder字符串生成工具

    主要生成StringBuilder 字符串 类似 StringBuilder builder = new StringBuilder(); builder.AppendFormat("&lt;span class=\"navSep\"&gt;&lt;/span&gt;\r\n"); builder.AppendFormat("机构看盘&lt;/a&gt;\r\n"); builder....

    显示 toString() 方法用法的 Java 程序.docx

    toString() 方法是 StringBuilder 类的内置方法,用于返回表示 StringBuilder 对象包含的数据的字符串。它创建并初始化一个新的 String 对象,以从该 StringBuilder 对象中获取字符序列,然后通过 toString() 返回 ...

    java中stringBuilder的用法.pdf

    文档中还提到了 `getSqlMapClientTemplate().queryForList((new StringBuilder()).append(entityClass.getName()).append(".select").toString(),null);` 这行代码展示了如何使用StringBuilder构建SQL查询语句的表名...

    浅析JAVA中toString方法的作用

    `toString()`方法在处理`StringBuffer`或`StringBuilder`类时特别有用,这两个类用于构建和修改字符串。由于`println()`方法不直接接受`StringBuffer`或`StringBuilder`对象,我们需要先调用`toString()`将其转换为`...

    StringBuilder类

    除了这些基本操作,StringBuilder还提供了一些其他有用的方法,如`reverse()`用于反转字符串内容,`toString()`用于将StringBuilder对象转换为不可变的String对象。在多线程环境下,如果多个线程同时修改同一个...

    Java StringBuilder

    8. **转换为String**:`toString()`方法可以将`StringBuilder`对象转换为不可变的`String`对象。例如: ```java String str = sb.toString(); // 转换为String ``` 在实际编程中,特别是在循环或遍历过程中构建字符...

    PrintStream,StringBuilder,Formatter

    在Java编程语言中,`PrintStream`, `StringBuilder` 和 `Formatter` 是三个非常重要的类,分别用于不同的输出处理。理解并熟练使用这三个类是提升Java编程能力的关键。 首先,我们来详细了解一下`PrintStream`。它...

    C#源代码-使用StringBuilder来拼接HTML中的Table表格.zip

    6. **获取结果字符串**:使用StringBuilder的ToString()方法将构建的HTML字符串提取出来。 ```csharp string htmlTable = htmlBuilder.ToString(); ``` 7. **输出或渲染**:根据应用场景,你可以将生成的HTML字符...

    java StringBuilder详解

    例如,在遍历集合打印元素时,可以创建一个`StringBuilder`,然后在循环内调用`append()`方法,最后通过`toString()`获取完整的字符串。 总的来说,`StringBuilder`是Java中处理字符串拼接和修改的高效工具,了解其...

    在C#的类或结构中重写ToString方法的用法简介

    在C#编程语言中,`ToString()`方法是一个非常重要的成员,它允许你将对象转换为字符串形式。每个类都隐式地继承自`System.Object`类,因此所有的类都拥有`ToString()`方法。默认情况下,这个方法返回的是类型名加上...

    java中的 toString()方法实例代码

    一种解决方案是使用 StringBuilder 来实现字符串的拼接,而不是使用 toString() 方法。例如: ```java ArrayList&lt;ArrayList&lt;Integer&gt;&gt; datas = new ArrayList(); // ... StringBuilder builder = new StringBuilder...

    万能的toString

    在`toString()`方法中,可以使用`StringBuilder`或`StringBuffer`来构建字符串,以提高性能。特别是处理大量数据时,避免了字符串连接操作导致的大量内存分配。 ```java @Override public String toString() { ...

    C#中的StringBuilder的使用

    本文将深入探讨`StringBuilder`的使用方法,包括其初始化、扩容机制以及主要的方法应用,如`Append`、`AppendFormat`、`Insert`、`Remove`和`Replace`等。 ### 初始化与扩容 `StringBuilder`对象的创建有两种常见...

    String和StringBuilder类的区别

    string result2 = sb.ToString(); ``` ### 结论 综上所述,`String` 和 `StringBuilder` 类在.NET框架中的使用有着明显的区别。选择合适的类取决于具体的应用场景:如果需要处理静态或变化较小的数据,`String` 是...

    C#文章加空格源码 StringBuilder类

    同样,`Append`方法用于添加字符或字符串到`StringBuilder`实例的末尾。 在实际开发中,我们可能还需要处理更多复杂的情况,比如多选区、考虑换行符、保留特定格式等。这时,我们可以结合正则表达式或其他字符串...

    深入理解StringBuilder的使用方法

    此外,ToString()方法可以将StringBuilder转换回不可变的String对象。 8. **多线程环境** 需要注意的是,StringBuilder不是线程安全的,如果在多线程环境下同时修改同一个StringBuilder对象,可能会导致数据不一致...

    StringBuilder的用法.docx

    因为 `append()`、`reverse()` 等方法返回的是 StringBuilder 实例本身,所以我们可以连续调用这些方法,如下所示: ```java StringBuilder sb = new StringBuilder(); sb.append(123).append("abc").append(true); ...

    Java的StringBuilder类.pdf

    - 将StringBuilder转换为String:调用`toString()`方法,如`String s = sb.toString();` 这些基本操作和转换使得StringBuilder成为在需要处理字符串时的一个理想选择,尤其是在循环或其他需要动态构建字符串的场景...

    Java StringBuffer & StringBuilder.pdf

    将 `StringBuilder` 或 `StringBuffer` 转换为 `String` 很简单,只需要调用它们的 `toString()` 方法: ```java StringBuilder sb = new StringBuilder("Hello World"); String str = sb.toString(); ...

    Java StringBuilder类原理及常用方法

    2. `public String toString()`: 将当前StringBuilder对象转换为String对象。 StringBuilder的应用 ------------------- StringBuilder可以用来解决字符串拼接操作时的性能问题。例如,在进行大量字符串拼接操作时...

Global site tag (gtag.js) - Google Analytics