【3w1h1p】String类做一些总结

java基础中的String类是在腾讯课堂的渡一教育看的视频,在此整理一下笔记和扩充
个人感觉渡一教育搭配B站其它视频学基础效果奇佳
另外参考博客有:
JAVA常量池,一篇文章就足够入门了。(含图解)
==和equals区别
Java技术——你真的了解String类的intern()方法吗
instanceof有什么作用
java中instanceof用法

1.是什么?特点是?

String是一个字符串对象,属于引用数据类型。
特点
1)String类被final关键字修饰,意味着String类不能被继承,并且它的成员方法都默认为final方法;字符串一旦创建就不能再修改。
2)String类实现了Serializable(序列化)、CharSequence(字符串规范)、 Comparable(整体排序)接口。
3)String实例的值是通过字符数组实现字符串存储的。

public final class String
    implements java.io.Serializable, Comparable<String>, CharSequence {
    /** The value is used for character storage. */
    private final char value[];
  • String的不可变特性
    String类中private final char value[];
    长度—>final修饰的数组 数组长度本身不变 final修饰数组的地址也不变
    内容—>private修饰的属性 不能在类的外部访问

2.怎么样?如何创建?

  • String str = “aa”;直接将字符串常量复制给str(字符串常量池
  • String str = new String();无参数构造方法创建空的对象
  • String str = new String(“aa”)带string第项的构造方法创建对象
  • String str = new String(byte[])
  • String str = new String(char[]) 参数为char数组的构造方法
  • String str = new String(char value[], int offset, int count) 参数为char数组并且带有偏移量的构造方法
  • String str = new String(StringBuffer buffer)参数为StringBuffer的构造方法
  • String str = new String(StringBuilder builder) 参数为StringBuilder的构造方法

3.哪里是常问点?

==和equals方法的区别

String的equals是继承自Object类中的方法,重写后改变了规则,比较字符串中的字面值。

让我们看看源码来理解吧。==比较的是引用,所以比较的是地址。equals第一步比较也是比较地址。
注意:

对于基本类型来说,== 比较的是值是否相等;
对于引用类型来说,== 比较的是两个引用是否指向同一个对象地址(两者在内存中存放的地址(堆内存地址)是否指向同一个地方);

public boolean equals(Object anObject) {
        if (this == anObject) {
            return true;
        }
        if (anObject instanceof String) {
            String anotherString = (String)anObject;
            int n = value.length;
            if (n == anotherString.value.length) {
                char v1[] = value;
                char v2[] = anotherString.value;
                int i = 0;
                while (n-- != 0) {
                    if (v1[i] != v2[i])
                        return false;
                    i++;
                }
                return true;
            }
        }
        return false;
    }

//第1个if:如果地址一样就返回true,否则进一步判断
//第2个if:如果查看anObject是String类的一个实例,是则继续判断;如果 anObject不是String类类的一个实例,或者anObject是 null,则返回 false。
//第3个if和while:进一步判断,如果value数组和anotherString.value数组字符比较一致,则字符序列一样,返回true,否则返回false
测试

        String a="abc";//地址在字符串常量
        String b=new String("abc");//在堆里开辟的地址
        System.out.println("a==b  "+(a==b));
        System.out.println("a.equals(b)  "+a.equals(b));
        String s1=new String("tom");
        String s2 =new String("tom");
        System.out.println("s1==s2 "+(s1==s2));
        System.out.println("s1.equals(s2) "+s1.equals(s2));
a==b  false
a.equals(b)  true
s1==s2 false
s1.equals(s2) true

intern方法

运行时常量池在方法区)
intern目的是为了重用String,虽然会增加程序运行时间,但是远远比内存GC回收花费的时间少。
归功于intern方法,这个方法首先在常量池中查找是否存在一份equal相等的字符串如果有的话就返回该字符串的引用,没有的话就将它加入到字符串常量池中,所以存在于class中的常量池并非固定不变的,可以用intern方法加入新的

public native String intern();

测试

        String str1 = new String("tom") + new String("cat");
        System.out.println(str1.intern() == str1);
        System.out.println(str1 == "tomcat");
        System.out.println(str1.equals("tomcat"));
true
true
true

String常用方法

  • 比较方法
    boolean equals(Object anObject)
    将此字符串与指定的对象比较。
    boolean equalsIgnoreCase(String anotherString)
    将此 String 与另一个 String 比较,不考虑大小写。
    int compareTo(Object o)
    把这个字符串和另一个对象比较。
    int compareTo(String anotherString)
    按字典顺序比较两个字符串。
    int compareToIgnoreCase(String str)
    按字典顺序比较两个字符串,不考虑大小写。
    boolean = contains(CharSequence s)
    判断给定的s是否在字符串中存在
  • 特殊方法
    int hashCode()
    返回此字符串的哈希码。
    char charAt(int index)
    返回给定index位置对应的字符
    int length()
    返回此字符串的长度。
    String intern()
    返回字符串对象的规范化表示形式。
    String toString()
    返回此对象本身(它已经是一个字符串!)。
    String format(String format, Object… args)
    使用指定的格式字符串和参数返回格式化的字符串
    String concat(String str)
    将指定字符串连接到此字符串的结尾。

将给定的str拼接在当前String对象的后面
注意: 方法执行完毕需要接受返回值 String的不可变特性
concat方法与 +拼接的性能问题
开发中若遇到频繁的拼接字符串—>通常使用StringBuilder/StringBuffer

  • 前缀-后缀
    boolean startsWith(String prefix)
    测试此字符串是否以指定的前缀开始。
    boolean startsWith(String prefix, int toffset)
    测试此字符串从指定索引开始的子字符串是否以指定前缀开始。
    boolean endsWith(String suffix)
    测试此字符串是否以指定的后缀结束。

  • 索引方法
    int indexOf(int ch)
    返回指定字符在此字符串中第一次出现处的索引。
    int indexOf(int ch, int fromIndex)
    返回在此字符串中第一次出现指定字符处的索引,从指定的索引开始搜索。
    int indexOf(String str)
    返回指定子字符串在此字符串中第一次出现处的索引。
    int indexOf(String str, int fromIndex)
    返回指定子字符串在此字符串中第一次出现处的索引,从指定的索引开始。
    int lastIndexOf(int ch)
    返回指定字符在此字符串中最后一次出现处的索引。
    int lastIndexOf(int ch, int fromIndex)
    返回指定字符在此字符串中最后一次出现处的索引,从指定的索引处开始进行反向搜索。
    int lastIndexOf(String str)
    返回指定子字符串在此字符串中最右边出现处的索引。
    int lastIndexOf(String str, int fromIndex)
    返回指定子字符串在此字符串中最后一次出现处的索引,从指定的索引开始反向搜索。

  • 匹配方法
    boolean matches(String regex)
    告知此字符串是否匹配给定的正则表达式。
    String replace(char oldChar, char newChar)
    返回一个新的字符串,它是通过用 newChar 替换此字符串中出现的所有 oldChar 得到的。
    String replaceAll(String regex, String replacement)
    使用给定的 replacement 替换此字符串所有匹配给定的正则表达式的子字符串。
    String replaceFirst(String regex, String replacement)
    使用给定的 replacement 替换此字符串匹配给定的正则表达式的第一个子字符串。
    String[] split(String regex)
    根据给定正则表达式的匹配拆分此字符串。
    String[] split(String regex, int limit)
    根据匹配给定的正则表达式来拆分此字符串。

  • 返回子序列
    CharSequence subSequence(int beginIndex, int endIndex)
    返回一个新的字符序列,它是此序列的一个子序列。

  • 截取
    String substring(int beginIndex)
    返回一个新的字符串,它是此字符串的一个子字符串。
    String substring(int beginIndex, int endIndex)
    返回一个新字符串,它是此字符串的一个子字符串。

  • 转换
    char[] toCharArray()
    将此字符串转换为一个新的字符数组。
    String toLowerCase()
    使用默认语言环境的规则将此 String 中的所有字符都转换为小写。
    String toLowerCase(Locale locale)
    使用给定 Locale 的规则将此 String 中的所有字符都转换为小写。
    String toUpperCase()
    使用默认语言环境的规则将此 String 中的所有字符都转换为大写。
    String toUpperCase(Locale locale)
    使用给定 Locale 的规则将此 String 中的所有字符都转换为大写。

  • 其它
    String trim()
    返回字符串的副本,忽略前导空白和尾部空白。
    static String valueOf(primitive data type x)
    返回给定data type类型x参数的字符串表示形式。
    byte[] getBytes()
    使用平台的默认字符集将此 String 编码为 byte 序列,并将结果存储到一个新的 byte 数组中。
    byte[] getBytes(String charsetName)
    使用指定的字符集将此 String 编码为 byte 序列,并将结果存储到一个新的 byte 数组中。
    void getChars(int srcBegin, int srcEnd, char[] dst, int dstBegin)
    将字符从此字符串复制到目标字符数组。

4.扩展

String与StringBuffer区别

String和StringBuilder区别 | String和StringBuffer区别

String不可变字符串
JDK1.0出现:
有一个接口Comparable
不可变体现在长度及内容
有一些方法StringBuilder没有 concat compareTo toUpperCase

StringBuilder可变字符串
JDK1.5出现:
有一个接口Appendable
可变字符串 没有final修饰 底层可以进行数组扩容
有一些方法String没有 append() insert() delete() reverse()
//特别注意是final带来变化

StringBuffer与StringBuilder区别

StringBuffer早期版本1.0 StringBuilder后来的版本1.5 早期版本 线程同步
安全性比较高 执行效率相对较低 后期版本 线程非同步 安全性比较低 执行效率相对较高
//特别注意synchronized带来的变化


名词解释

常量池
简单地理解就是一个临时的池子,在编译期间存放class文件的字面值和符号引用。
字面值是指文本字符串、被声明为final的常量值、基本数据类型的值;符号引用是指类和结构的完全限定名、字段名称和描述符、方法名称和描述符。

运行时常量池
类加载器会加载对应的class文件,而上面的常量池会被类加载进入运行时常量池,此时是存在内存里的拥有内存地址,运行时常量池是全局共享的,多个类共用一个运行时常量池。

字符串常量池
字符串常量池是存放字符串的,即常量池中的文本字符串在类加载时进入字符串常量池。字符串常量池也是在堆中。

可变字符串
可变字符串即StringBuffer与StringBuilder,在字符串缓冲区。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值