首页 > 编程语言 >Java基础学习(八)

Java基础学习(八)

时间:2025-01-17 21:44:50浏览次数:1  
标签:Java String StringBuilder 基础 学习 str 创建 字符串 public

Java基础学习(八):字符串

目录

本文为个人学习记录,内容学习自 黑马程序员


概述

  • java.lang 包是 Java 的核心包,其下的类都是无需手动导入即可使用的
  • java.lang.String 是字符串类,Java 程序中所有字符串都为此类的对象

字符串的创建

创建 String 对象有两种方式:

  • 直接赋值:String name = "victoria";

  • 使用 new 创建:

    构造方法 说明
    public String() 创建空白字符串,不含任何内容
    public String(String original) 根据传入的字符串,创建字符串对象
    public String(char[] chs) 根据字符数组,创建字符串对象
    public String(byte[] chs) 根据字节数组,查ASCII码表,创建字符串对象

字符串内存分析

  • 存储位置:

    • 直接赋值得到的字符串存储在字符串常量池(StringTable)中,在 JDK7 之前字符串常量池位于方法区中,后来移到了堆中
    • 通过 new 创建的字符串存储在堆中
  • 底层机制:

    • 通过直接赋值创建字符串时,如果字符串常量池中没有该常量,则创建一个新常量,并将地址传给字符串变量;如果字符串常量池中已经有了该常量,则会复用该常量

      String a = "abc";						// a存储的地址值为 0x0011
      String b = "abc";						// b存储的地址值为 0x0011
      
    • 使用 new 创建的字符串和其他对象的创建一样,会在堆中开辟新内存存储数据,不存在相同字符串的复用

      char[] chs = {'a', 'b', 'c'};
      String a = new String(chs);				// a存储的地址值为 0x0011
      String b = new String(chs);				// b存储的地址值为 0x0022
      
  • 总结:使用直接赋值不仅简单,还节约内存


String 类常用方法

  1. 字符串的比较

    由于引用数据类型的变量存储的是地址值,因此会出现下面的比较问题:

    String a = "abc";
    String b = "abc";
    System.out.println(a == b);					// 输出为 true
    
    String a = new String("abc");
    String b = new String("abc");
    System.out.println(a == b);					// 输出为 false
    

    小知识:使用 Scanner 从键盘接收的字符串也是 new 创建的

    为了实现对字符串本身的比较,String 类提供了两种方法:

    • equals():完全一样结果为true,否则为false
    • equalsIgnoreCase():不区分大小写
    String a = new String("abc");
    String b = new String("abc");
    boolean result = a.equals(b);
    boolean result2 = a.equalsIgnoreCase(b);
    
  2. 字符串按索引获得字符

    通过调用 charAt() 方法实现

    String str = "abc";
    char ch = str.charAt(1);
    System.out.println(ch);						// 输出为 'b'
    
  3. 获取字符串长度

    通过调用 length() 方法实现

    String str = "abc";
    int len = str.length();
    System.out.println(len);					// 输出为 3
    
  4. 截取字符串

    通过调用 substring() 方法实现

    两种实现方法:

    • String substring(int beginIndex, int endIndex) :第一个参数表示起始索引,第二个参数表示结束索引(不包含)
    • String substring(int beginIndex):给定起始索引,默认截取到末尾

    注意:1. 包头不包尾,包左不包右,2. 需要通过返回值接收截取后的字符串,因为字符串本身是不可修改的

    String str = "abc";
    String subStr1 = str.substring(0, 2);
    String subStr2 = str.substring(1);
    System.out.println(subStr1);				// 输出为 "ab"
    System.out.println(subStr2);				// 输出为 "bc"
    
  5. 字符串替换

    通过调用 replace() 方法实现

    注意:需要通过返回值接收替换后的结果

    String str = "abcaaacba";
    String str2 = str.replace("aaa", "bbb");
    System.out.println(str2);					// 输出为 "abcbbbcba"
    
  6. 字符串提取字符数组

    通过调用 toCharArray() 方法实现

    用途:常用于修改字符串内容

    String str = "abc";
    char[] chs = str.toCharArray();				// 得到的chs为['a', 'b', 'c']
    

StringBuilder 类

  • java.lang.StringBuilder 可以看成一个容器,创建之后里面的内容是可变的

  • 作用:提高字符串的操作效率

  • 两种构造方式:无参和有参

    构造方法 说明
    public StringBuilder() 创建一个空白可变字符串对象,不含任何内容
    public StringBuilder(String str) 根据字符串的内容,来创建可变字符串对象
  • 常用方法:

    方法名 说明
    public StringBuilder append(任意类型) 添加数据,并返回对象本身
    public StringBuilder reverse() 反转容器中的内容
    public int length() 返回长度(字符出现的个数)
    public String toString() 把 StringBuilder 转换成 String
  • 返回值是自身 vs 无返回值

    • 相同点:都不需要创建一个新的变量用于接收返回值
    • 不同点:返回值是自身时可以用于链式编程
  • 方法示例:

    StringBuilder sb = new StringBuilder();
    // append方法
    sb.append(1).append('a').append("zz");					// 链式编程
    System.out.println(sb);									// 输出为 "1azz"(和 String 类似,Java 底层在实现打印输出时进行了特殊处理,不是输出地址值,而是属性值)
    // reverse方法
    sb.reverse();
    System.out.println(sb);									// 输出为 "zza1"
    // length方法
    int len = sb.length();
    System.out.println(len);								// 输出为 4
    // toString方法
    String str = sb.toString();
    System.out.println(str);								// 输出为 "zza1"
    

StringJoiner 类

  • java.util.StringJoiner 也可以看成一个容器,创建之后里面的内容是可变的

  • 作用:提高字符串的操作效率,而且代码编写简洁,但由于在 JDK8 才出现,因此使用不广

  • 两种构造方式:只有有参

    构造方法 说明
    public StringJoiner(String str) 创建一个StringJoiner对象,指定拼接时的间隔符号
    public StringJoiner(String str, String str, String str) 创建一个StringJoiner对象,指定拼接时间隔符号、开始符号、结束符号
  • 常用方法:

    方法名 说明
    public StringJoiner add(String str) 添加数据(只能添加字符串),并返回对象本身
    public int length() 返回长度(字符出现的个数)
    public String toString() 把 StringJoiner 转换成 String
  • 方法示例:

    StringJoiner sj = new StringJoiner(", ", "[", "]");
    sj.add("aaa").add("bbb").add("ccc");
    System.out.println(sj);										// 输出为 "[aaa, bbb, ccc]"
    int len = sj.length();
    System.out.println(len);									// 输出为 15
    String str = sj.toString();
    System.out.println(str);									// 输出为 "[aaa, bbb, ccc]"
    

字符串相关类底层原理

  1. 字符串存储的内存原理

    • 直接赋值:会复用字符串常量池中的
    • new创建:不会复用,而是开辟一个新的空间
  2. == 号比较的到底是什么?

    • 基本数据类型:比较数据值
    • 引用数据类型:比较地址值
  3. 字符串拼接的底层原理

    • 拼接时等号右边没有变量:会触发字符串的优化机制,在编译的时候就已经是最终结果了

      下例中,引用变量 s 中存储的是字符串常量池中 "abc" 的地址

      String s = "a" + "b" + "c";			===>			String s = "abc";
      
    • 拼接时等号右边有变量:

      • JDK8 之前:会在堆中创建新的 StringBuilder 对象和 String 对象

        下例中,引用变量 s2 中存储的是堆中新建的 String 对象的地址

        String s1 = "a";
        String s2 = s1 + "b";	===>	String s2 = new StringBuilder().append(s1).append("b").toString();
        
      • JDK8 之后:会先预估最终字符串长度,并创建一个数组存储该字符串,最后通过数组在堆中创建一个新的字符串

    • 总结:拼接时等号右边没有变量时,拼接后的新字符串存储在字符串常量池中;等号右边有变量时,拼接后新字符串存储在堆中

  4. StringBuilder 提高效率原理

    • 将所有要拼接的内容放到 StringBuilder 中,不会创建很多无用的空间,可以节约内存
  5. StringBuilder 扩容机制

    • StringBuilder 中的数据存储在 byte[] 数组中
    • StringBuilder 有 容量长度 两个概念,容量表征了最多容纳的字符个数,长度表征已经容纳的字符个数
    • 默认的容量为16,当长度超出了默认容量时,会进行一次扩容,将容量扩成34,如果还是超出容量,则容量大小以实际长度为准

标签:Java,String,StringBuilder,基础,学习,str,创建,字符串,public
From: https://www.cnblogs.com/victoria6013/p/18677708

相关文章

  • node.js在线学习系统程序+论文 可用于毕业设计
    本系统(程序+源码+数据库+调试部署+开发环境)带文档lw万字以上,文末可获取源码系统程序文件列表开题报告内容选题背景关于在线学习系统的研究,现有研究主要以系统的部分功能优化、特定课程的线上教学实践为主。在国外,一些发达国家早已开展在线学习系统的建设与应用,取得了显著......
  • 深度学习中的损失函数:从原理到实践
    在深度学习的广袤领域中,损失函数(LossFunction)宛如指引模型训练方向的北极星,其重要性不言而喻。它不仅量化了模型预测与真实值之间的差距,更是优化算法调整模型参数的依据。本文将深入探讨几种常见的损失函数,从原理剖析到实际应用,带你领略它们在深度学习中的独特魅力。一、IoUL......
  • Linux基础:文件系统&目录操作
    Linux基础:文件系统&目录操作文件系统Linux本质上就是一个文件系统,Linux文件系统是操作系统组织、存取、保存数据的一种手段。整体采用层级式的倒状树目录结构。倒状树结构中的目录/:根目录,Linux中的绝对路径就是由这个开始的/bin:主要存放系统的普通指令/boot:主要存放......
  • 51单片机学习日记:独立按键控制LED灯
    我们可以再单片机上看到4个独立的按键,控制一个LED灯的亮灭先用第一个就可以,我们先找到独立按键的原理图来看看如何通过按键来控制LED灯的亮灭;独立按键的一段接地,另一端接P3,则我们按下按键时会使端口为低电平,我们就可以通过逻辑:当P31=0(按下去按键)时让灯亮,当P31=1时灯灭。(大......
  • 密码学——密码学基础、散列函数与数字签名
    1.密码学概述是信息安全的基础和核心,是防范各种安全威胁的重要手段,信息安全的许多相关知识都与密码学相关。密码学发展密码学是一门古老而又年轻的学科,几千年以前就存在,至今仍在发展演进。地位非常重要甚至起决定性作用。密码学源于希腊语kryptós,意为“隐藏的”。最早的......
  • THREE.js学习笔记8——Textures
    这个小节主要学习纹理,Texture纹理是覆盖几何形状表面的图像,不同类型的纹理具有多种不同的效果。这些纹理(尤其是金属性和粗糙度)遵循PBR原则基于物理的渲染许多技术往往遵循现实生活中的方向以获得现实的结果成为现实渲染的标准许多软件、引擎和库都在使用它如何加载纹理?......
  • 《offer 来了:Java 面试核心知识点精讲 -- 原理篇》
    在Java面试的战场上,只知皮毛可不行,面试官们越来越看重对原理的理解。今天就给大家分享一本能让你在面试中脱颖而出的“武林秘籍”——《offer来了:Java面试核心知识点精讲--原理篇》。本书详细介绍了Java架构师在BAT和移动互联网公司面试中常被问及的核心知识,内容详细......
  • Java数组详解
    目录一、什么是数组二、声明和创建1、数组的声明2、数组的创建三、数组的初始化1.静态初始化(StaticInitialization)2.动态初始化(DynamicInitialization)3.默认初始化(DefaultInitialization)四、数组的基本使用1、访问元素2、数组长度3、遍历数组五、数组下......
  • 机器学习笔记合集
    大家好,这里是好评笔记,公主号:Goodnote。本笔记的任务是解读机器学习实践/面试过程中可能会用到的知识点,内容通俗易懂,入门、实习和校招轻松搞定。笔记介绍本笔记的任务是解读机器学习实践/面试过程中可能会用到的知识点,内容通俗易懂,入门、实习和校招轻松搞定。涵盖机器......
  • 每天一个优秀提示词学习收藏 - 文本去AI化(四)
    ......