Test code
```java String str=new String(""); StringBuffer buffer=new StringBuffer(""); StringBuilder builder=new StringBuilder(""); long startTime=0L; long endTime=0L; startTime=System.currentTimeMillis(); for (int i=0;i<20000;i++){ buffer.append(String.valueOf(i)); } endTime=System.currentTimeMillis(); System.out.println(endTime-startTime); startTime=System.currentTimeMillis(); for (int i=0;i<20000;i++){ builder.append(String.valueOf(i)); } endTime=System.currentTimeMillis(); System.out.println(endTime-startTime);
``
result
for the first time :

The second time :

third time :

StringBuffer And StringBuilder All inherit the parent class AbstractStringBuilder,
StringBuffer And StringBuilder The difference is that... Is added to the method synchronized Modifier , So said StringBuffer For multithreading ,
But in general StringBuffer and StringBuilder Variables of type are only declared inside the method , Instead of sharing in multiple threads , So you don't usually have to worry about multithreading , Use it directly StringBuilder that will do ,
As for efficiency , because JDK 1.6 Began to introduce bias lock 、 Lightweight lock , in other words JDK Yes synchronized Optimized , So in a single thread StringBuffer Performance is no better than StringBuilder Bad .
I hope it helps you .
The difference between them is thread safety , You can get a multithreaded environment test , You're still testing a single thread , So it doesn't make sense for you to test like this ,