Java 常用类 02 Integer缓冲区与String

Java 常用类 02 Integer缓冲区与String,第1张

Java 常用类 02 Integer缓冲区与String 2.1 Integer 缓冲区

面试题:

Integer integer1 = new Integer(100);
Integer integer2 = new Integer(100);

System.out.println(integer1 == integer2);

Integer integer3 = 100;
Integer integer4 = 100;

System.out.println(integer3 == integer4);

Integer integer5 = 200;
Integer integer6 = 200;

System.out.println(integer5 == integer6);


为什么会出现这样的 情况呢 ??

解析:

我们不难发现,第一个 false 的原因 是由于 用了 构造器,开辟了 两块空间在 堆里面,然后比较的 是 内存地址。而并非内容的 100.所以是 false。


第二个的情况在于,反汇编查看,发现 自动装箱 调用的是 valueOf() 方法,所以导致 true 的原因可能是 调用了 该方法。

那么 为什么 第三组 的比较,用的 也是自动装箱,比较后是 fasle 呢? 这就要去 看下 源码了。


看源码可知,原来 提供的 数字,必须在一定范围内,才不会调用 构造器。所以 可能 200 这个数字 超过了这个 范围。那么这个范围是多大呢?


最小是 = -128
最大是 = 127


然后在此 基础上,开辟了 一个 128 + 127 + 1 = 256 个 元素的 Integer 数组。用来 存放 -128 ~ 127 这些数字。

我们把这个称其为 Integer 的缓冲区,也就是 有 一部分 数字是已经 预留存在的。被存放在了 这个 256 个元素的 数组里。所以 当我们 想要 封装 Integer 数字的时候,如果是这些预留的 数字。我们就可以 直接 把对应的内存地址 发给你。

经过这么 一刨析,也就是 100 这个数字,在 自动装箱的时候,是 同一个地址。因为指向的都是 那个数组里面 对应的100这个数字的内存地址。所以相等。而 超过了 128 这个最大限度的 200,是需要 用到 构造器的,那么 回过头来 内存地址 肯定还是不一样的,所以第三组 比较的结果还是 false

  • 那为什么要 开辟 这样的 缓冲区呢?

答:因为 在实际开发中,这些 数字 运用的 都非常的 频繁。它们也是 28 的 有符号位范围(-27 ~ 27-1)


2.2 String 类
  • 字符串是常量,创建之后不可改变。这里指的是 如果字符串池里没有 你创建的字符序列,那么就会被放进去。而一旦放入,就无法被更改。等到 再次碰到 这个字符串的时候,就会 实施共享。
  • 字符串的字面值是会被存储到 字符串池里面的,可以共享。

如果使用 new 的方式 去创建 String 变量,那么 地址肯定就不一样了。


原因 在于 当 new 的时候,虽然 字面值 会被存储到 字符串池里,但是 也在 堆里 开辟了一个空间,用来 存储 字符串池 中 该字符串的 地址。也就是下面的过程


那么 最后 栈区 存储的地址,不还是 两个 不一样的 内存地址吗。只不过 这两个 不一样的 内存,存储的 字符串池里的 内存地址 是一样的。

切记:new 的 String,肯定 是 在堆区 和 字符串池 里 都 开辟了 一个空间。

  • String 常用的方法
  1. public int length(): 返回字符串的长度(是指一个字符 算一个,并不是 按照 中文2个字节,英文和数字1个字节来计算的。)

  2. public char charAt(int index):根据下标获取字符

  3. public boolean contains(String str):判断当前字符串中是否包含str子串。

  4. public char[] toCharArray():将字符串转为 char 类型数组。

  5. public int indexOf(String str):从头部开始查找 str 子串 第一次出现的位置。不存在 则 返回 -1;

  6. public int lastIndexOf(String str):从尾部开始查找 str 子串 第一次出现的位置。不存在 则 返回 -1;

  7. public String trim():去掉字符串前后的空格

  8. public String toUpperCase():将小写转成大写。

  9. public boolean endsWith(String str):判断字符串是否以 str 结尾。

  10. public boolean startsWith(String str):判断字符串是否以 str 开头。

  11. public String toLowerCase():将大写转为小写

  12. public String repalace(char oldChar,char newChar):将旧字符串替换成新字符串

  13. split() 对字符串进行拆分(可以 与 正则表达式连用)

  14. equals() 比较 是否相等。

  15. compareTo() 比较 大小,通过 编码来比较。

  16. equalsIgnoreCase(); 忽略大小写 比较 是否相等。


案例:

package com.muquanyu.www.Two;

public class String案例 {
    public static void main(String[] args) {
        String str = "this is a text";
        String []temp = str.split(" ");

        for(String x:temp){
            System.out.println(x);
        }

        str.replace("text","practice");

        str.replace("practice","text");

        str.replace("text","easy text");

        String[]tempB = new String[5];

        for(int i = 0;i < 4;++i){
            tempB[i] = temp[i];
        }

        tempB[3] = "easy";
        tempB[4] = "text";

        for(String x:tempB){
            System.out.print(x+" ");
        }
        System.out.println();

        for(int i = 0;i < 4;++i){
            char[]charr = temp[i].toCharArray();
            charr[0] = Character.toUpperCase(charr[0]);
            temp[i] = new String(charr);
            System.out.print(temp[i]+" ");
        }
    }
}

欢迎分享,转载请注明来源:内存溢出

原文地址:https://54852.com/zaji/4658446.html

(0)
打赏 微信扫一扫微信扫一扫 支付宝扫一扫支付宝扫一扫
上一篇 2022-11-06
下一篇2022-11-06

发表评论

登录后才能评论

评论列表(0条)

    保存