JAVA 字符串(六)

字符串(六)

String

String是java定义好的一个类,定义在java.lang包中,使用时不需导包。

String类的特点

  • Java程序中所有的双引号字符串,都是String类的对象。
  • 字符串不可变,它的对象在创建后不可更改,若想更改,只能用新的对象做替换。
  • 字符串虽然不可改变,但是可以被共享
    • 字符串常量池:StringTable,当使用双引号双剑字符串对象时,会检查常量池中是否存在该数据。若不存在,则创建;若存在,则复用。
    • jdk7之前:StringTable在方法区中
    • jdk7开始:StringTable在堆内存中

String s1="abc";
String s2="abc";
System.out.println(s1==s2);//true

创建String对象的两种方式

  1. 直接赋值
    • String 名称=“内容”;
    • :当使用双引号直接赋值时,系统会检查该字符串在串池中是否存在,不存在则创建新的,存在则复用。
  2. new 构造方法:
    • public String() 创建空白字符串
    • public String(String original) 根据传入的字符串,创建字符串对象
    • public String(char[] chs) 根据字符数组,创建字符串对象
    • public String(byte[] chs) 根据字节数组,创建字符串对象
    • :每new一次都会在堆内存中开一块儿新的空间

:

public class Test{
    public static void main(String[] args){
        //直接赋值
        String s1="ljsblog";
        System.out.println(s1);

        //new
        //空参构造
        String s2=new String();
        System.out.println(s2);
        //传递字符串
        String s3=new String("ljsblog");
        System.out.println(s3);
        //传递字符数组
        //可以修改字符串的内容
        char ch[]={'l','j','s','b','l','o','g'};
        String s4=new String(ch);
        System.out.println(s4);
        //传递字节数组
        //网络中传输的数据就是字节信息
        byte by[]={108,106,115,98,108,111,103};
        String s5=new String(by);
        System.out.println(s5);
    }
}
/*
ljsblog

ljsblog
ljsblog
ljsblog
*/

字符串方法

equals和equalsIgnoreCase
  • boolean equals(要比较的字符串)
    • 完全一样才是true,否则false
  • boolean equalsIgnoreCase(要比较的字符串)
    • 忽视大小写的比较

:

public class Test{
    public static void main(String[] args){
        String s1="ljs";
        String s2=new String("ljs");
        String s3="LJS";

        System.out.println(s1.equals(s2));//true
        System.out.println(s1.equals(s3));//false
        System.out.println(s2.equalsIgnoreCase(s3));//true
    }
}

注:==号比较的内容

  • 基本数据类型比较的是数据值
  • 引用数据类型比较的是地址值
public class Test{
    public static void main(String[] args){
        String s1="ljsblog";//s1存储串池的地址值
        String s2=new String("ljsblog");//s2存储堆里面的地址值
        System.out.println(s1==s2);//false
    }
}
charAt

public char charAt(int index)
根据索引返回字符

length

public int length()
返回字符串长度

substring

String substring(int beginIndex,int endIndex)
按范围截取字符串,包头不包尾,只有返回值才是截取的字符串
String substring(int beginIndex)
从给出地址截取到末尾

replace

String replace(旧值,新值)
替换

toCharArray

char[] toCharArray()
将字符串变为字符数组。

split

String[] split(String regex)
切割字符串
若正常指定切割规则,发现没有得到自己想要的数据,可尝试在规则前加入\\。

范例
//已知正确的用户名和密码,请用程序实现模拟用户登录,共三次机会,并给出登录成功失败的相应提示
import java.util.Scanner;
public class Test{
    public static void main(String[] args){
        //定义用户名和密码
        String user="ljs";
        String pass="123456";

        //循环三次
        Scanner s=new Scanner(System.in);
        for(int i=0;i<3;i++){
            //录入密码账号
            System.out.print("请输入用户名:");
            String str1=s.next();
            System.out.print("请输入密码:");
            String str2=s.next();
            //若对比成功则退出
            if(user.equals(str1) && pass.equals(str2)){
                System.out.println("登录成功");
                break;
            }else{//对比不成继续循环
                if(i==2){
                    System.out.println("登录失败,您的账户已被锁定。");
                }else {
                    System.out.println("登录失败,请重新登入,您还剩余" + (2 - i) + "次机会");
                }
            }
        }
    }
}
//输入一个字符串,统计其小写字母,大写字母,数字的个数
import java.util.Scanner;
public class Test{
    public static void main(String[] args){
        //录取字符串
        Scanner sc=new Scanner(System.in);
        System.out.print("请输入字符串:");
        String s=sc.next();
        int lower=0;
        int upper=0;
        int num=0;
        for(int i=0;i<s.length();i++){
            if(s.charAt(i)>='a' && s.charAt(i)<='z'){
                lower++;
            }else if(s.charAt(i)>='A' && s.charAt(i)<='Z'){
                upper++;
            }else if(s.charAt(i)>='0' && s.charAt(i)<='9'){
                num++;
            }
        }
        System.out.println("大写字母:"+lower+" 小写字母:"+upper+" 数字"+num);
    }
}
//创建一个方法,输入一个字符串,将其逆序返回,并输出
import java.util.Scanner;
public class Test{
    public static void main(String[] args){
        Scanner sc=new Scanner(System.in);
        String s=sc.next();
        System.out.println(reverse(s));
    }
    public static String reverse(String s){
        String sr="";
        for(int i=s.length()-1;i>=0;i--){
            sr=sr+s.charAt(i);
        }
        return sr;
    }
}
//金额转换,例如:输入3199,输出零佰零拾零万叁仟壹佰玖拾玖元
import java.util.Scanner;
public class Test{
    public static void main(String[] args){
        //输入金额
        Scanner s=new Scanner(System.in);
        System.out.print("请输入您的金额:");
        int num=s.nextInt();
        //单位转换
        String sc="";

        while(true){
            int w=num%10;
            sc=convert(w)+sc;
            num/=10;
            if(num==0){
                break;
            }
        }
        int n=7-sc.length();
        for(int i=0;i<n;i++)
        {
            sc="零"+sc;
        }
        String sum="";
        String[] danwei={"佰","拾","万","仟","佰","拾","元"};
        for(int i=0;i<7;i++){
            sum=sum+sc.charAt(i)+danwei[i];
        }
        System.out.println(sum);
    }
    public static String convert(int num){
        String[] s={"零","壹","贰","叁","肆","伍","陆","柒","捌","玖"};
        return s[num];
    }
}
//输入身份证号打印如下信息:
//出生日期:xxxx年X月X日
//性别:男/女
import java.util.Scanner;
public class Test {
    public static void main(String[] args) {
        Scanner s = new Scanner(System.in);
        System.out.print("请输入您的身份证号:");
        String id = s.next();
        System.out.println("出生日期:" + id.substring(6, 10) + "年" + id.substring(10, 12) + "月" + id.substring(12, 14) + "日");
        if ((id.charAt(16) - 48) % 2 == 0) {
            System.out.println("性别:女");
        } else {
            System.out.println("性别:男");
        }
    }
}
//游戏敏感词替换
import java.util.Scanner;
public class Test{
    public static void main(String[] args){
        String[] s={"cnm","lj","mlgb","nt","fw"};
        Scanner sc=new Scanner(System.in);
        System.out.print("请输入你要说的话:");
        String talk=sc.next();
        for(int i=0;i<s.length;i++){
            talk=talk.replace(s[i],"***");
        }
        System.out.print(talk);
    }
}

StringBuilder

StringBuilder可看成一个容器,创建之后里面内容可变。
使用场景

  • 字符串拼接
  • 字符串反转

构造方法

public StringBuilder()

  • 创建一个空白可变字符串对象,不含有任何内容
  • StringBuilder sb=new StringBuilder()

public StringBuilder(String str)

  • 根据字符串的内容,创建可变字符串对象
  • StringBuilder sb=new StringBuilder(“ljsblog”)

常用方法

append

public StringBuilder append(任意类型)
添加数据,返回对象本身

reverse

public StringBuilder reverse()
反转内容

length

public int length()
返回字符串长度

toString

public String toString()
将StringBuilder转换为String

范例
public class Test{
    public static void main(String[] args){
        //创建对象
        StringBuilder sb=new StringBuilder();
        //添加字符串
        sb.append("ljsblog");
        sb.append(123);
        sb.append(12.3);
        System.out.println(sb);
        //反转字符串
        sb.reverse();
        System.out.println(sb);
        //求字符串长度
        int len=sb.length();
        System.out.println(len);
        //将StringBuilder变为String
        String s=sb.toString();
        System.out.println(s);
    }
}

StringJoiner

StringJoiner跟StringBuilder一样,也可以看做一个可修改的容器,创建之后里面的内容是可变的。
作用:提高字符串的操作效率,代码编写简洁,JDK8出现

构造方法

public StringJoiner(间隔符号)

  • 创建一个StringJoiner对象,指定拼接时的间隔符号

public StringJoiner(间隔符号,开始符号,结束符号)

  • 创建一个StringJoiner对象,指定拼接时的间隔符号,开始符号,结束符号

常用方法

add

public StringJoiner add(添加的内容)
添加数据,并返回对象本身

length

public int length()
返回字符串长度(包括间隔符)

toString

public String toString()
返回拼接之后的字符串

范例
public class Test{
    public static void main(String[] args){
        //创建对象
        StringJoiner sj=new StringJoiner(",","[","]");
        //添加内容
        sj.add("aaa");
        sj.add("bbb");
        sj.add("bbb");
        System.out.println(sj);
        //求长度
        int len=sj.length();
        System.out.println(len);
        //将StringJoiner转换为String
        String s=sj.toString();
        System.out.println(s);
    }
}
/*
[aaa,bbb,bbb]
13
[aaa,bbb,bbb]
*/

链式编程

调用一个方法时,返回的结果是对象,就可以继续向下调用方法。
:

public class Test{
    public static void main(String[] args){
        StringBuilder sb=new StringBuilder();
        sb.append("ljs").append("blog").append(1).reverse();
        System.out.println(sb);
    }
}
/*
1golbsjl
*/
//输入一个字符串,判断是否对称
import java.util.Scanner;
public class Test{
    public static void main(String[] args){
        Scanner s=new Scanner(System.in);
        String s1=s.next();
        String s2=new StringBuilder(s1).reverse().toString();
        if(s1.equals(s2)){
            System.out.println("对称字符串");
        }else{
            System.out.println("非对称字符串");
        }
    }
}
//将int[] arr={1,2,3,4,5,6}里面的内容转换成[1,2,3,4,5,6]输出
public class Test{
    public static void main(String[] args){
        int[] arr={1,2,3,4,5,6};
        String s=joiner(arr);
        System.out.println(s);

    }
    public static String joiner(int[] arr){
        StringJoiner sj=new StringJoiner(",","[","]");
        for(int i=0;i<arr.length;i++){
            sj.add(""+arr[i]);
        }
        return sj.toString();
    }
}
/*
[1,2,3,4,5,6]
*/

字符串底层原理

字符串拼接

  • 字符串拼接时,若有变量:
    • JDK8前:系统底层会自动创建一个StringBuilder对象,再调用append方法完成拼接,拼接后,再调用toString方法转换成String类型,而toString方法的底层原理是直接new了一个字符串对象
    • JDK8:系统预估字符串拼接后的大小,把拼接的内容放在数组中,此时也产生一个新的字符串
  • 若无变量:
    • 字符串直接相加,编译之后就是拼接后的结果,会复用串池中的字符串

StringBuilder提高效率

所有要拼接的内容都会往StringBuilder中放,不会创造无用的空间,节约内存

StringBuilder源码分析

  1. 默认创建一个容量为16的字节数组(注:容量是最多装多少,长度是实际装了多少)
  2. 添加的内容小于当前容量,直接存
  3. 大于当前容量,则扩大容量,原来的容量*2+2
  4. 若还不够,则以实际长度为准

StringBuilder和StringBuffer的区别

StringBufferStringBuilder中的方法和功能完全是等价的,
只是StringBuffer中的方法大都采用了synchronized关键字进行修饰,因此是线程安全的, 而StringBuilder没有这个修饰,可以被认为是线程不安全的 。
在单线程程序下,StringBuilder效率更快,因为它不需要加锁,不具备多线程安全而StringBuffer则每次都需要判断锁,效率相对更低

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值