java之字符串详解

String类

构造方法

  • String(String original):创建一个字符串对象
  • String(char[] value):把数组数据封装成字符串对象
  • String(char[] value, int index, int count):把数组一部分封装成字符串对象。

常用方法

判断

  • boolean equals(Object obj):判断2个字符串是否相等。
  • boolean equalsIgnoreCase(String s):忽略大小写判断2个字符串是否相同。
  • boolean startsWith(String str):判断字符串是否以str开头。
  • boolean endsWith(String str):判断字符串是否以str结尾。
  • boolean contains(String str):判断是否包含str字符串

获取

  • int length():获取字符串长度
  • char charAt(int index):获取指定索引处的字符
  • int indexOf(String str):获取str第一次出现的索引
  • String substring(int start):从start开始截取字符串
  • String substring(int start,int end):从start开始到end截取字符串

转换

  • char[] toCharArray() 把字符串转成字符数组。
  • String toLowerCase() 把字符串全小写。
  • String toUpperCase() 把字符串全大写。

其他

  • String trim() 把两边空格去掉。
  • String[] split(String str) 分割字符串。

StringBuilder与StringBuffer

并对其做了追加和插入操作。这些操作修改了 str 对象的值,而没有创建新的对象,这就是 StringBuilder 和 String 最大的区别。

StringBuilder s=new StringBuilder("hello");
s.append("world");//追加方法
s.insert(5," "); //插入方法
s.reverse();//翻转字符串

StringBuilder与StringBuffer的区别

StringBuilder 和 StringBuffer 之间的最大不同在于 StringBuilder 的方法不是线程安全的(不能同步访问)。由于 StringBuilder 相较于 StringBuffer 有速度优势,所以多数情况下建议使用 StringBuilder 类。然而在应用程序要求线程安全的情况下,则必须使用 StringBuffer 类。

String常量池

为什么需要常量池

  • 字符串的分配,和其他的对象分配一样,耗费高昂的时间与空间代价,作为最基础的数据类型,大量频繁的创建字符串,极大程度地影响程序的性能
  • JVM为了提高性能和减少内存开销,在实例化字符串常量的时候进行了一些优化,为字符串开辟一个字符串常量池,类似于缓存区。
  • 创建字符串常量时,首先坚持字符串常量池是否存在该字符串,存在该字符串,返回引用实例,不存在,实例化该字符串并放入池中。

为什么String设计成不可变的

  1. 字符串常量池的需要。字符串常量池的诞生是为了提升效率和减少内存分配。可以说我们编程有百分之八十的时间在处理字符串,而处理的字符串中有很大概率会出现重复的情况。正因为String的不可变性,常量池很容易被管理和优化。

  2. 安全性考虑。正因为使用字符串的场景如此之多,所以设计成不可变可以有效的防止字符串被有意或者无意的篡改。从java源码中String的设计中我们不难发现,该类被final修饰,同时所有的属性都被final修饰,在源码中也未暴露任何成员变量的修改方法。(当然如果我们想,通过反射或者Unsafe直接操作内存的手段也可以实现对所谓不可变String的修改)。

  3. 作为HashMap、HashTable等hash型数据key的必要。因为不可变的设计,jvm底层很容易在缓存String对象的时候缓存其hashcode,这样在执行效率上会大大提升。

经典面试题

  • new String(“abc”)创建几个对象?
    简单的回答是一个或者两个,如果是常量区有值为"abc"的值,则只在堆中创建一个对象;如果常量区没有则会在常量区创建"abc",此处的常量区是方法区的运行时常量池(也称为动态常量区)。
    new都会在堆中创建对象。直接String s = "xxx"不会涉及堆,只在常量区检查是否有该常量。

  • intern()方法
    在调用”ab”.intern()方法的时候会返回”ab”,但是这个方法会首先检查字符串池中是否有”ab”这个字符串,如果存在则返回这个字符串的引用,否则就将这个字符串添加到字符串池中,然会返回这个字符串的引用。

发布了23 篇原创文章 · 获赞 1 · 访问量 512

猜你喜欢

转载自blog.csdn.net/qq_38783257/article/details/103551406