专栏名称: Java专栏
一个Java、Python、数据库、中间件、业内资讯、面试、学习资源等干货的知识分享社区。
目录
相关文章推荐
中国能建  ·  一图读懂|中国能建科技创新大会 ·  11 小时前  
中国能建  ·  全名单!“十四五”科技创新表彰 ·  11 小时前  
一条漫画  ·  女友丝袜破了,男领导又送了她一双 ·  16 小时前  
中国保利  ·  一个兑现幸福的地方! ·  昨天  
一条漫画  ·  清纯女友变海王,表格写满了用人感受 ·  2 天前  
51好读  ›  专栏  ›  Java专栏

昨天还在for循环里写加号拼接字符串的那个同事,今天已经不在了

Java专栏  · 公众号  ·  · 2021-01-25 12:20

正文

引言


都说 StringBuilder 在处理字符串拼接上效率要强于 String,但有时候我们的理解可能会存在一定的偏差。最近我在测试数据导入效率的时候就发现我以前对 StringBuilder 的部分理解是错误的。后来我通过实践测试 + 找原理 的方式搞清楚了这块的逻辑。现在将过程分享给大家。


测试用例


我们的代码在循环中拼接字符串一般有两种情况:


  • 第一种就是每次循环将对象中的几个字段拼接成一个新字段,再赋值给对象

  • 第二种操作是在循环外创建一个字符串对象,每次循环向该字符串拼接新的内容。循环结束后得到拼接好的字符串


对于这两种情况,我创建了两个对照组。


第一组:


在每次 For 循环中拼接字符串,即拼即用、用完即毁。分别使用 String 和 StringBuilder 拼接

/** * 循环内 String 拼接字符串,一次循环后销毁 */public static void useString(){  for (int i = 0; i < CYCLE_NUM_BIGGER; i++) {    String str = str1 + i + str2 + i + str3 + i + str4 ;  }}
/** * 循环内 使用 StringBuilder 拼接字符串,一次循环后销毁 */public static void useStringBuilder(){  for (int i = 0; i < CYCLE_NUM_BIGGER; i++) {    StringBuilder sb = new StringBuilder();    String s = sb.append(str1).append(i).append(str2).append(i).append(str3).append(i).append(str4).toString();  }}

第二组:


多次 For 循环拼接一个字符串,循环结束后使用字符串,使用后由垃圾回收器回收。也是分别使用 String 和 StringBuilder 拼接。

 * 多次循环拼接成一个字符串 用 String/** */public static void useStringSpliceOneStr (){  String str = "";  for (int i = 0; i < CYCLE_NUM_LOWER; i++) {    str += str1 + str2 + str3 + str4 + i;  }}
/** * 多次循环拼接成一个字符串 用 StringBuilder */public static void useStringBuilderSpliceOneStr(){  StringBuilder sb = new StringBuilder();  for (int i = 0; i < CYCLE_NUM_LOWER; i++) {    sb.append(str1).append(str2).append(str3).append(str4).append(i);  }}

为了保证测试质量,在每个测试项目进行前。线程休息 2s,之后空跑 5 次热身。最后执行 5 次求平均时间的方式计算时间

public static int executeSometime(int kind, int num) throws InterruptedException {  Thread.sleep(2000);  int sum = 0;  for (int i = 0; i < num + 5; i++) {    long begin = System.currentTimeMillis();
   switch (kind){      case 1:        useString();        break;      case 2:        useStringBuilder();        break;      case 3:        useStringSpliceOneStr();        break;      case 4:        useStringBuilderSpliceOneStr();        break;      default:        return 0;    }
   long end = System.currentTimeMillis();
   if(i > 5){      sum += (end - begin);    }  }  return sum / num;}

主方法

public class StringTest {    public static






请到「今天看啥」查看全文