学习String源码的部分方法

先看构造器:

 
 
private final char value[];  //char类型的数组   以下均会用到
private int hash;  //缓存字符串的哈希值  //以下均会用到
public String() {
        this.value = "".value;  //声明时没有参数 则直接用空.value获取该value值,这个.value不太懂,个人认为应该是类似是将一个整体字符串,分割成char类型数组的方法。
    }
 public String(String original) {
        this.value = original.value;  //当存在值的时候 就将该值放到value中,也就是char类型的数组
        this.hash = original.hash;  //以及对应的哈希值
    }
public String(char value[]) {  //这个构造器说明了 String其实就是一个char类型的数组
        this.value = Arrays.copyOf(value, value.length);
    }
public String(char value[], int offset, int count) {  //给定起始下标和指定位数的构造器
        if (offset < 0) {  //先判断给定下标值是否符合逻辑,小于0则报字符串下标越界异常
            throw new StringIndexOutOfBoundsException(offset);
        }
        if (count <= 0) {
            if (count < 0) {  //再判断截取的位数是否符合逻辑,小于0同样包异常
                throw new StringIndexOutOfBoundsException(count);
            }
            if (offset <= value.length) {  //如果起始下标小于等于字符数组长度,那么这个字符数组达不到截取的长度,直接返回空即可。
                this.value = "".value;
                return;
            }
        }
        // Note: offset or count might be near -1>>>1.
        if (offset > value.length - count) {  //如果起始位置大于字符数组总长度减去截取长度也会报异常
            throw new StringIndexOutOfBoundsException(offset + count);
        }
        this.value = Arrays.copyOfRange(value, offset, offset+count);
    }

其他的构造参数也就类似以上四种,就不再一一列举。

然后就是比较常用的equals

public boolean equals(Object anObject) {
        if (this == anObject) {  //判断调用对象和传入对象的地址是不是一样的 如果一致则直接判断相同
            return true;
        }
        if (anObject instanceof String) {  //如果地址值不相同 则判断传入参数是否属于String类型
            String anotherString = (String)anObject;  //属于的话进行强转
            int n = value.length;
            if (n == anotherString.value.length) {  //判断转成字符串格式的传入参数长度是否跟要比较的字符串长度一样,不一样则直接返回false
                char v1[] = value;
                char v2[] = anotherString.value;
                int i = 0;
                while (n-- != 0) {  //长度一样的情况下,将两个字符串生成的字符数据挨个进行对比,用的其实还是==或者!=的方法,有一个不等于则返回false。
                    if (v1[i] != v2[i])
                        return false;
                    i++;
                }
                return true;  //只有两个字符数字完全比较完,没有不相同的才会返回true;
            }
        }
        return false;
    }

截取字符串substring

public String substring(int beginIndex) {
        if (beginIndex < 0) {  //判断开始下标是否合理
            throw new StringIndexOutOfBoundsException(beginIndex);
        }
        int subLen = value.length - beginIndex;  //比较字符串长度跟起始下标相减得到想要截取的长度 判断是否大于0,不大于则代表数组越界
                                //个人感觉直接判断起始下标跟总长度-1不就可以吗?可能是需要截取的长度本来就要用,所以直接拿截取长度跟0作比较了
if (subLen < 0) { throw new StringIndexOutOfBoundsException(subLen); } return (beginIndex == 0) ? this : new String(value, beginIndex, subLen); //如果截取起始下标为0,那就还返回整个字符串,如果不是则返回一个新字符串。 }

猜你喜欢

转载自www.cnblogs.com/qcq0703/p/12044474.html