Java基础笔记 – String字符串详解 字符串实现原理 StringBuffer
本文由发表于6年前 | Java基础 | 评论数 1 |  被围观 8,913 views+
1、String类的equals方法:1.1、Object类的equals方法:1.2、String类的equals方法:1.3、总结:2、equals()方法重写的例子:3、String字符串详解:3.1、拼接字符串时创建对象:3.2、创建String对象的两种方法:3.3、intern方法:4、StringBuffer类:
1、String类的equals方法:

String类的equals方法继承自Object类,但是由于重写了,所以实现了不一样的功能。
首先看到Object类的equals方法:

1.1、Object类的equals方法:
equals
public boolean equals(Object obj)
指示其他某个对象是否与此对象“相等”。
equals 方法在非空对象引用上实现相等关系:
•	自反性:对于任何非空引用值 x,x.equals(x) 都应返回 true。
•	对称性:对于任何非空引用值 x 和 y,当且仅当 y.equals(x) 返回 true 时,x.equals(y) 才应返回 true。
•	传递性:对于任何非空引用值 x、y 和 z,如果 x.equals(y) 返回 true,并且 y.equals(z) 返回 true,那么 x.equals(z) 应返回 true。
•	一致性:对于任何非空引用值 x 和 y,多次调用 x.equals(y) 始终返回 true 或始终返回 false,前提是对象上 equals 比较中所用的信息没有被修改。
•	对于任何非空引用值 x,x.equals(null) 都应返回 false。

查看该方法的源代码如下:

public boolean equals(Object obj) {
    return (this == obj);
    }

可以发现,Object类的equals方法使用了“==”判断,其功能是判断了比较的两个对象的引用地址是不是一样,判断是不是同一个对象。

下面看String类的equals方法:

1.2、String类的equals方法:
equals
public boolean equals(Object anObject)
将此字符串与指定的对象比较。当且仅当该参数不为 null,并且是与此对象表示相同字符序列的 String 对象时,结果才为 true。
覆盖:
类 Object 中的 equals
参数:
anObject - 与此 String 进行比较的对象。
返回:
如果给定对象表示的 String 与此 String 相等,则返回 true;否则返回 false。
另请参见:
compareTo(String), equalsIgnoreCase(String)

该方法的源代码如下:

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

可以发现,如果判断的不是同一个对象,继续判断比较的对象是不是Strinig类的实例,如果是的话就按照字符串的字面值进行判断,如果字面值相等,则返回true。

1.3、总结:

Object类中的equals方法判断两个引用是否一致,里面只是使用了==进行判断,等价于==。

String类的equals方法判断当前字符串与传进来的字符串的内容是否一致。

所以一般判断字符串相等都是用equals方法,而不使用==。

2、equals()方法重写的例子:

模仿String类的equals()方法实现,给一个类重写equals()方法实现特殊的比较规则:

class A{
    private String id;
    public A(String id){
        this.id = id;
    }
    @Override
    public boolean equals(Object obj) {
        if(this == obj){
            return true;
        } else if(obj instanceof A){
            A a = (A)obj;
            if(a.id.equals(this.id)){
                return true;
            }
        }
        return false;
    }
}
3、String字符串详解:
public final class String
extends Object
implements Serializable, Comparable<String>, CharSequence
String 类代表字符串。Java 程序中的所有字符串字面值(如 "abc" )都作为此类的实例实现。
字符串是常量;它们的值在创建之后不能更改。字符串缓冲区支持可变的字符串。因为 String 对象是不可变的,所以可以共享。例如:
     String str = "abc";

等效于:
     char data[] = {'a', 'b', 'c'};
     String str = new String(data);
3.1、拼接字符串时创建对象:

当使用+号拼接字符串时,会生成新的String对象,而不是向原有的String对象追加内容。

3.2、创建String对象的两种方法:


① 直接采用字符串赋值方式:

String str = “abc”;

首先查找String Pool中是否存在“abc”这个字符串对象,如果不存在,则在字符串池中创建该对象,并将String Pool中的该对象的地址返回来,赋给引用变量str。

如果存在,则不创建任何对象,而是直接把String Pool中的该对象地址返回并赋给str引用。


② 使用new关键字创建String:

String str = new String(“abc”);

如果在String Pool中存在“abc”这个字符串对象,则在队中创建“abc”字符串对象,然后将堆中的该对象地址返回并赋给str引用。

如果在String Pool中不存在“abc”字符串对象,则首先在String Pool中创建“abc”字符串对象,然后再在堆中创建一个,并返回队中的该对象地址,赋给str引用。

3.3、intern方法:
intern
public String intern()
返回字符串对象的规范化表示形式。
一个初始为空的字符串池,它由类 String 私有地维护。
当调用 intern 方法时,如果池已经包含一个等于此 String 对象的字符串(用 equals(Object) 方法确定),则返回池中的字符串。否则,将此 String 对象添加到池中,并返回此 String 对象的引用。
它遵循以下规则:对于任意两个字符串 s 和 t,当且仅当 s.equals(t) 为 true 时,s.intern() == t.intern() 才为 true。
所有字面值字符串和字符串赋值常量表达式都使用 intern 方法进行操作。字符串字面值在 Java Language Specification 的 §3.10.5 定义。
返回:
一个字符串,内容与此字符串相同,但一定取自具有唯一字符串的池。
4、StringBuffer类:
public final class StringBuffer
extends Object
implements Serializable, CharSequence

线程安全的可变字符序列。一个类似于 String 的字符串缓冲区,但不能修改。虽然在任意时间点上它都包含某种特定的字符序列,但通过某些方法调用可以改变该序列的长度和内容。

可将字符串缓冲区安全地用于多个线程。可以在必要时对这些方法进行同步,因此任意特定实例上的所有操作就好像是以串行顺序发生的,该顺序与所涉及的每个线程进行的方法调用顺序一致。

StringBuffer 上的主要操作是 append 和 insert 方法,可重载这些方法,以接受任意类型的数据。每个方法都能有效地将给定的数据转换成字符串,然后将该字符串的字符添加或插入到字符串缓冲区中。append 方法始终将这些字符添加到缓冲区的末端;而 insert 方法则在指定的点添加字符。

每个字符串缓冲区都有一定的容量。只要字符串缓冲区所包含的字符序列的长度没有超出此容量,就无需分配新的内部缓冲区数组。如果内部缓冲区溢出,则此容量自动增大。从 JDK 5 开始,为该类补充了一个单个线程使用的等价类,即 StringBuilder。与该类相比,通常应该优先使用 StringBuilder 类,因为它支持所有相同的操作,但由于它不执行同步,所以速度更快。

除了文章中有特别说明,均为IT宅原创文章,转载请以链接形式注明出处。
本文链接:http://www.itzhai.com/java-based-notebook-string-string-string-detailed-implementation-principle-stringbuffer.html
关键字: , ,
arthinking Java技术交流群:280755654,入门群:428693174 more
分享到:
 
2011 10/28
文章评论
    一条评论
给我留言

有人回复时邮件通知我
Java基础的相关文章
随机文章 本月热门 热评
1 UML笔记 UML统一建模语言介绍 UML图形的基本绘制 2011/10/9
2 Java基础笔记 – static与final关键字及其编写细节提示 2011/10/26
3 ExtJS获取ComboBox远程数据的JsonReader和本地数据的ArrayStore的写法 2011/8/6
4 XSS与HTTP-only Cookie 脚本获取JSESSIONID的方法 2012/1/30
5 扩展自jsoup的HTML XSS过滤程序 2015/3/9
6 JVM笔记 – 自动内存管理机制(Java内存区域与内存溢出异常) 2014/11/11
友情推荐 更多
破博客 文官洗碗安天下,武将打怪定乾坤。多么美好的年代,思之令人泪落。
Mr.5's Life 白天是一名程序员,晚上就是个有抱负的探索者
行知-追寻技术之美 关注大数据,分布式系统
我爱编程 编程成长轨迹
Cynthia's Blog 学习笔记 知识总结 思考感悟
 
猜您喜欢
欢迎关注我的公众号 IT宅
关于IT宅 文章归档

IT宅中的文章除了标题注明转载或有特别说明的文章,均为IT宅的技术知识总结,学习笔记或随笔。如果喜欢,请使用文章下面提供的分享组件。转载请注明出处并加入文章的原链接。 感谢大家的支持。

联系我们:admin@itzhai.com

Theme by arthinking. Copyright © 2011-2015 IT宅.com 保留所有权利.