JAVA知识梳理二(String)

这篇博客主要梳理了JAVA中String类的相关知识,虽然内容有些混乱,但提到了常用的部分。博主认为理解这些核心概念就足够了,不必全部记住,除非是为了面试。未来博主将不再深入探讨基础数据类型的源码,认为这对于实际工作帮助有限。
摘要由CSDN通过智能技术生成
  • 后半部分我发现非常常用就懒得写了,说实话,String有点乱的,大致知道这些东西,以后写的话直接翻源码就可以了,没必要全记住,除非面试,以后也不会在写基础数据相关的源码了,看一下就可以,对我来说感觉没啥用


package java.lang;

import java.io.ObjectStreamField;
import java.io.UnsupportedEncodingException;
import java.nio.charset.Charset;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.Comparator;
import java.util.Formatter;
import java.util.Locale;
import java.util.Objects;
import java.util.StringJoiner;
import java.util.regex.Matcher;
import java.util.regex.Pattern;
import java.util.regex.PatternSyntaxException;

//java.io.Serializable,序列化
//Comparable<String> 对比实例化对象的大小,         只有【public int compareTo(T o);】一个方法
/**CharSequence只读的字符序列,相对比较重要,可能需要读一下,里边有
	- int length();
	- char charAt(int index);
	- CharSequence subSequence(int start, int end);
	- public String toString();
	- public default IntStream chars()
	- public default IntStream codePoints()
几个方法
*/
public final class String
    implements java.io.Serializable, Comparable<String>, CharSequence {
   
    //字符存储
    private final char value[];

    //hash值存储
    private int hash; // Default to 0
	//这是两个重要的变量,值存入value,哈希值存入hash用于对比,不需要对比时频繁的计算hash值

	//实现序列化的标识
    private static final long serialVersionUID = -6849794470754667710L;

  	//序列化时使用
    private static final ObjectStreamField[] serialPersistentFields =
        new ObjectStreamField[0];

	//下边是一大堆String的构造方法,看你new的时候传入什么值就调用相应的方法,具体实现直接看代码就可以了。
    public String() {
   
        this.value = "".value;
    }

    public String(String original) {
   
        this.value = original.value;
        this.hash = original.hash;
    }

    public String(char value[]) {
   
        this.value = Arrays.copyOf(value, value.length);
    }


    public String(char value[], int offset, int count) {
   
        if (offset < 0) {
   
            throw new StringIndexOutOfBoundsException(offset);
        }
        if (count <= 0) {
   
            if (count < 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);
    }

    public String(int[] codePoints, int offset, int count) {
   
        if (offset < 0) {
   
            throw new StringIndexOutOfBoundsException(offset);
        }
        if (count <= 0) {
   
            if (count < 0) {
   
                throw new StringIndexOutOfBoundsException(count);
            }
            if (offset <= codePoints.length) {
   
                this.value = "".value;
                return;
            }
        }
        // Note: offset or count might be near -1>>>1.
        if (offset > codePoints.length - count) {
   
            throw new StringIndexOutOfBoundsException(offset + count);
        }

        final int end = offset + count;

        // Pass 1: Compute precise size of char[]
        int n = count;
        for (int i = offset; i < end; i++) {
   
            int c = codePoints[i];
            if (Character.isBmpCodePoint(c))
                continue;
            else if (Character.isValidCodePoint(c))
                n++;
            else throw new IllegalArgumentException(Integer.toString(c));
        }

        // Pass 2: Allocate and fill in char[]
        final char[] v = new char[n];

        for (int i = offset, j = 0; i < end; i++, j++) {
   
            int c = codePoints[i];
            if (Character.isBmpCodePoint(c))
                v[j] = (char)c;
            else
                Character.toSurrogates(c, v, j++);
        }

        this.value = v;
    }

    @Deprecated
    public String(byte ascii[], int hibyte, int offset, int count) {
   
        checkBounds(ascii, offset, count);
        char value[] = new char[count];

        if (hibyte == 0) {
   
            for (int i = count; i-- > 0;) {
   
                value[i] = (char)(ascii[i + offset] & 0xff);
            }
        } else {
   
            hibyte <<= 8;
            for (int i = count; i-- > 0;) {
   
                value[i] = (char)(hibyte | (ascii[i + offset] & 0xff));
            }
        }
        this.value = value;
    }

    @Deprecated
    public String(byte ascii[], int hibyte) {
   
        this(ascii, hibyte, 0, ascii.length);
    }

	//在String构造函数中用于检查边界,也就是检查传入的offset和length是否正确
    private static void checkBounds(byte[] bytes, int offset, int length) {
   
        if (length < 0)
            throw new StringIndexOutOfBoundsException(length);
        if (offset < 0)
            throw new StringIndexOutOfBoundsException(offset);
        if (offset > bytes.length - length)
            throw new StringIndexOutOfBoundsException(offset + length);
    }

    public String(byte bytes[], int offset, int length, String charsetName)
            throws UnsupportedEncodingException {
   
        if (charsetName == null)
            throw new NullPointerException("charsetName");
        checkBounds(bytes, offset, length);
        this.value = StringCoding.decode(charsetName, bytes, offset, length);
    }

    public String(byte bytes[], int offset, int length, Charset charset) {
   
        if (charset == null)
            throw new NullPointerException("charset");
        checkBounds(bytes, offset, length);
        this.value =  StringCoding.decode(charset, bytes, offset, length);
    }

    public String(byte bytes[], String charsetName)
            throws UnsupportedEncodingException {
   
        this(bytes, 0, bytes.length, charsetName);
    }

    public String(byte bytes[], Charset charset) {
   
        this(bytes, 0, bytes.length, charset);
    }

    public String(byte bytes[], int offset, int length) {
   
        checkBounds(bytes, offset, length);
        this.value = StringCoding.decode(bytes, offset, length);
    }

    public String(byte bytes[]) {
   
        this(bytes, 0, bytes.length);
    }

    public String(StringBuffer buffer) {
   
        synchronized(buffer) {
   
            this.value = Arrays.copyOf(buffer.getValue(), buffer.length());
        }
    }

    public String(StringBuilder builder) {
   
        this.value = Arrays.copyOf(builder.getValue(), builder.length());
    }
	//打包私有构造函数,它为speed.this构造函数共享值数组,总是需要使用share == true来调用。需要单独的构造函数,因为我们已经有一个公共String(char [])构造函数,它可以复制给定的char[]。参数share,用来区别于String(char[])构造器的
    String(char[] value, boolean share) {
   
        // assert share : "unshared not supported";
        this.value = value;
    }

	//返回字符串长度,长度为字符串Unicode的个数,
    public int length() {
   
        return value.length;
    }

	//判断字符串是否为空
    public boolean isEmpty() {
   
        return value.length == 0;
    }

	//返回位于指定索引的单个字符
    public char charAt(int index) {
   
        if ((index < 0) || (index >= value.length)) {
   
            throw new StringIndexOutOfBoundsException(index);
        }
        return value[index];
    }

	//返回指定索引处的字符(Unicode 代码点)。索引引用 char 值(Unicode 代码单元),其范围从 0 到 length() - 1。
    public int codePointAt(int index) {
   
        if ((index < 0) || (index >= value.length)) {
   
            throw new StringIndexOutOfBoundsException(index);
        }
        return Character.codePointAtImpl(value, index, value.length);
    }

	//返回指定索引之前的字符
    public int codePointBefore(int index) {
   
        int i = index - 1;
        if ((i < 0) || (i >= value.length)) {
   
            throw new StringIndexOutOfBoundsException(index);
        }
        return Character.codePointBeforeImpl(value, index, 0);
    }

   //准确计算beginIndex到endIndex之间的unicode字符的数量,感觉没有什么用处就是了
    public int codePointCount(int beginIndex, int endIndex) {
   
        if (beginIndex < 0 || endIndex > value.length || beginIndex > endIndex) {
   
            throw new IndexOutOfBoundsException
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值