StringBuffer类和StringBuilder类[java]

目录

⛳️概述

⛳️StringBuffer和StringBuilder中常用的方法

1.构造方法

2.添加功能

3.删除功能

4.替换功能

5.反转功能

 6.截取功能

7.获取功能

⛳️String、StringBuffer、StringBuilder的异同

1.相同点

2.不同点


⛳️概述

都是可变的字符序列,我们如果对字符串进行拼接操作,每次拼接,都会构建一个新的String对象,既耗时又浪费空间,这个时候就需要使用StringBuffer或StringBuilder来解决这个问题,当需要考虑线程安全的场景下,使用StringBuffer,如果不需要考虑线程安全,追求效率的情况下,可以使用StringBuilder

  • 对可变的的理解:

案例:

public class StringBufferDemo {
    public static void main(String[] args) {
        StringBuffer stringBuffer = new StringBuffer("abcd");长度为20
        //向末尾追加内容
        stringBuffer.append("efg111111");//加进去长度还没有超过20
        stringBuffer.append("efg222222");//加进去长度超过20,此时就要重新创建底层的数组
    }
}

以debug模式运行:

①开始时StringBuffer的地址值是487,value数组是492

StringBuffer类和StringBuilder类[java]_第1张图片

②当count是13时两个地址值都没有变

StringBuffer类和StringBuilder类[java]_第2张图片

 ③此时StringBuffer的地址仍然是487,而value数组变成了497

StringBuffer类和StringBuilder类[java]_第3张图片

 所以当向StringBuffer中添加内容时,是将内容添加到底层的数组中,数组没有被final修饰,变的是底层数组(char[] value),而不是StringBuffer对象,当数组装满时,会创建一个新的数组,将新数组地址给底层数组,StringBuffer对象是不会改变的

  • StringBuffer、StringBuilder和String类似,底层也是用char数组来存储字符串的值,并且数组的默认长度为16,即一个空的StringBuffer对象数组长度为16,实例化一个StringBuffer对象即创建了一个大小为16个字符的字符串缓冲区,但是当我们调用有参构造函数创建一个StringBuffer对象时,数组长度就不再是16了,而是根据当前对象的值来决定数组的长度,数组的长度=当前对象字符串的长度+16;所以一个StringBuffer创建完成之后,有16个字符空间可以对其值进行修改,修改的时候,会先判断StringBuffer对象原来的char数组的容量能不能装下新的字符串,如果装不下则会对char数组进行扩容

⛳️StringBuffer和StringBuilder中常用的方法

1.构造方法

①public StringBuffer()

  • 构造一个没有字符的字符缓冲区,初始容量为16个字符

②public StringBuffer(String str)

  • 构造一个初始化为指定字符串内容的字符串缓冲区

  • 长度为字符串长度加默认长度(16)

③public StringBuffer(int capacity)

  • 构造一个指定初始容量的没有字符的字符缓冲区

2.添加功能

①public StringBuffer append(String str)

  • 拼接字符串

②public StringBuffer insert(int offset,String str)

  • 在指定位置插入指定的内容

案例:

public class StringBufferDemo {
    public static void main(String[] args) {
       StringBuffer stringBuffer = new StringBuffer("abcd");
           //向末尾追加内容
           stringBuffer.append("efg111");
           System.out.println(stringBuffer);//abcdefg111
 
       StringBuffer stringBuffer1 = new StringBuffer("abcd");
           //向指定的位置插入字符串       
           stringBuffer1.insert(2,"xx");
           System.out.println(stringBuffer1);//abxxcd
    }
}

3.删除功能

①public StringBuffer deleteCharAt(int index)

  • 删除指定位置的内容

②public StringBuffer delete(int start,int end)

  • 删除指定范围的内容,左闭右开

案例:

public class StringBufferDemo1 {
    public static void main(String[] args) {
       StringBuffer stringBuffer = new StringBuffer("abcd");
          //删除指定位置的内容       
          stringBuffer.deleteCharAt(1);
          System.out.println(stringBuffer);//acd
        
       StringBuffer stringBuffer1 = new StringBuffer("abcdefg");
          //删除指定区间的内容,包含开始,不包含结束
          stringBuffer.delete(0,3);
          System.out.println(stringBuffer1);//defg
    }
}

4.替换功能

public StringBuffer replace(int start,int end,String str)

  • 替换指定范围的内容

案例:

public class StringBufferDemo2 {
    public static void main(String[] args) {
       StringBuffer stringBuffer =    new StringBuffer("abcdefg");
          //替换
          stringBuffer.replace(2,5, "XXX");
          System.out.println(stringBuffer);//abXXXfg
    }
}

5.反转功能

public StringBuffer reverse()

  • 把当前字符串序列逆转

案例:

public class StringBufferDemo3 {
    public static void main(String[] args) {
       StringBuffer stringBuffer = new StringBuffer("abcdefg");
          //逆序字符串            
          stringBuffer.reverse();
          System.out.println(stringBuffer);//gfedcba
    }
}        

 6.截取功能

①public String substring(int start)

  • 截取一个字符串副本返回

②public String substring(int start,int end)

  • 返回指定范围的子字符串

截取功能和前面几个功能的不同,返回值类型是String类型,不是直接在数组上操作的,是在原来的串上截取了一段,赋给了一个新的字符串,相当于截取了一个副本回来,原来的字符串不变

案例:

public class StringBufferDemo4 {
    public static void main(String[] args) {
       StringBuffer stringBuffer1 = new StringBuffer("abcdefg");
               //截取一个字符串副本返回          
               String sub =  stringBuffer1.substring(2);
               System.out.println(sub);//cdefg
               //stringBuffer不变
               System.out.println(stringBuffer1);//abcdefg
        
       StringBuffer stringBuffer2 = new StringBuffer("qwertyu");
               //截取一个字符串副本返回
               String sub =  stringBuffer.substring(2,5);
               System.out.println(sub);//ert
               //stringBuffer不变
               System.out.println(stringBuffer);//qwertyu
       }
}

7.获取功能

int length()

  • 返回底层数组中实际装入的字符个数

案例:

public class StringBufferDemo4 {
    public static void main(String[] args) {
               String s1 = "qwer";
               System.out.println(s1.length());//4
               //返回的是底层数组中实际装入的字符个数
         StringBuffer stringBuffer = new StringBuffer("qwqqwqw");
               System.out.println(stringBuffer.length());//7 
    }
}

StringBuilder类功能和StringBuffer功能完全一致,有区别的是StringBuffer是线程安全的

方法实现(源码):

StringBuilder方法实现:
        @Override
        public StringBuilder append(String str) {
            super.append(str);
            return this;
        }
StringBuffer方法实现:加上了synchronized同步锁,一次只允许一个线程进入方法操作,不允许两个线程同时进入操作
        @Override
        public synchronized StringBuffer append(String str) {
            toStringCache = null;
            super.append(str);
            return this;
        }

StringBuffer和StringBuilder常用方法总结:

StringBuffer append(xxx):拼接字符串
StringBuffer delete(int start,int end):删除指定范围的内容,左开右闭
StringBuffer replace(int start, int end, String str):替换指定范围的内容
StringBuffer insert(int offset, xxx):在指定位置插入指定的内容
StringBuffer reverse() :把当前字符序列逆转
​
public int indexOf(String str) : 返回指定子字符串在当前字符串中第一次出现处的索引
public String substring(int start,int end) :返回指定范围的子字符串
public int length() : 返回字符串的长度
public char charAt(int n ) : 获取指定索引处的字符
public void setCharAt(int n ,char ch) : 设置指定索引处的字符

⛳️String、StringBuffer、StringBuilder的异同

String:适用于少量的字符串操作的情况

StringBuffer:适用于单线程下在字符缓冲区进行大量操作的情况

StringBuilder:适用多线程下在字符缓冲区进行大量操作的情况

1.相同点

  • 底层都是通过char数组实现的

2.不同点

  • String对象一旦创建,其值不能改变,如果要修改,会重新开辟内存空间来修改存储之后的对象;而StringBuffer和StringBuilder对象的值是可以被修改的

  • StringBuffer几乎所有的方法都使用synchronized实现了同步,线程比较安全,在多线程系统中可以保证数据同步,但是效率较低;而StringBuilder没有实现同步,线程不安全,在多线程系统中不能使用StringBuilder,但是效率比较高

  • 在实际开发中,如果需要对字符串进行频繁的修改,就要避免使用String,否则会造成内存空间浪费,当需要考虑线程安全的场景下,使用StringBuffer,如果不需要考虑线程安全,追求效率的情况下,可以使用StringBuilder

你可能感兴趣的:(java,后端)