本文精华
Ctrl+alt+t选中代码然后idea会提示用什么去包围
for循环 知道循环的次数 知道循环的范围去用
while循环知道循环的停止条件的时候去用
输出的内容是分散的要用字符串拼接
print和println的区别
String substring(int beginIndex,int endIndex)
截取索引 注意点:包头不包尾 包左不包右 只有返回值是截取的小段 所以要有返回值
String substring(int beginIndex)截取到末尾
String replace(旧值,新值)替换
注意点:只有返回值才是替换之后的结果
字符串拼接如果太多的话用s=s+“abc”数据量太大很长时间 所以要用
Ctrl+n出现搜索界面
ctrl+f12搜索里面的方法
ctrl+b更进
目录
需求:键盘接受一个字符串,程序判断该字符串是不是对称字符串,并且打印结果
今天是几个字符串练习的案例
案例one 金额转换
我们会遇到阿拉伯数字对个十百千的转换
代码思路
查表法
将阿拉伯数字先变成大写的汉字 ——我们可以先把大写的汉字存在一个数组中用0-9分别代表每个汉字 然后用charAt对数字进行遍历 然后挨个对应就ok
int money = sc.nextInt(); 这边要用int去接收的话 需要用nextint
然后先对money进行安全检验:
在安全检验的过程中 如果用户输入的数字有错就要去重新去输入所以我们要用ctrl+alt+t去包裹
选择用while语句(输入正确的时候去停止)
刚开始写的代码是int money = sc.nextInt();这样在循环里面所以循环外面使用不了money
所以我们把money定义到外面int money; money=sc.next;
到这里金额录入完毕 现在去做查表法
自己定义一个方法可以把数字变成大写的中文
public static String getCapitalNumber(int number){
String[] arr={"零","壹","贰","叁","肆","伍","六","柒","八","玖",};
return arr[number];
在想办法得到money里面的每一个数字
定义空字符串
用while语句 /%得到每一个数字 并且调用getCapitalNumber方法输出大写数字 但是输出的内容是分散的要用字符串拼接 所以我们在外面定义一个空字符串
String moneyStr="";
把转换后的大写拼接到moneyStr中
moneyStr=moneyStr+CapitalNumber;
发现运行成果是倒着
只需要稍微修改一下代码 调换一下位置即可
moneyStr=CapitalNumber+moneyStr;
第三步就是把空位补零补到七位
int count=7-moneyStr.length();
for (int i = 0; i < count; i++) {
moneyStr="零"+moneyStr;
}
最后一部分就是插入单位 ===>查表法
我们可以定义一个数组去表示单位
String[] arr={"佰","拾","万","千","佰","十","元"};
遍历moneyStr 然后再把arr的单位插进去
这边插单位的时候需要去用moneyStr.length().fori去循环
print和println的区别
System.out.println("hello world!!!");//输出数据并换行
System.out.print("welcome");//输出不换行
System.out.print(" here!");//输出不换行
/*输出结果:
hello world!!!
welcome here!
*/
for (int i = 0; i < moneyStr.length(); i++) {
char c=moneyStr.charAt(i);
System.out.print(c);
System.out.print(arr[i]);
}
但是打印出来的不太好 我们把它拼接成一个字符串
就是需要用result=result+c+arr[i];
代码展示
import java.util.Scanner;
public class StringDemo {
public static void main(String[] args) {
Scanner sc = new Scanner(System.in);
int money;
while (true) {
System.out.println("请输入一行金额:");
money = sc.nextInt();
if (money >= 0 && money <= 9999999) {
break;
} else {
System.out.println("请输入七位以下正确的金额:");
}
}
String moneyStr="";
//得到money里面的每一位数字
while (true) {
int ge=money%10;
String CapitalNumber=getCapitalNumber(ge);
moneyStr=CapitalNumber+moneyStr;
money=money/10;
if(money==0){
break;
}
}
int count=7-moneyStr.length();
for (int i = 0; i < count; i++) {
moneyStr="零"+moneyStr;
}
String[] arr={"佰","拾","万","千","佰","十","元"};
String result="";
// for (int i = 0; i < moneyStr.length(); i++) {
// char c=moneyStr.charAt(i);
// System.out.print(c);
// System.out.print(arr[i]);
// }
for (int i = 0; i < moneyStr.length(); i++) {
char c=moneyStr.charAt(i);
result=result+c+arr[i];
}
System.out.println(result);
}
public static String getCapitalNumber(int number){
String[] arr = {"零", "壹", "贰", "叁", "肆", "伍", "六", "柒", "八", "玖"};
return arr[number];
}
}
案例two 手机号屏蔽
今天的案例是手机号屏蔽
代码思路
先去获取一个手机号
String phonenumber="13112349468";
然后直接用
String substring(int beginIndex,int endIndex)
截取索引
注意点:包头不包尾 包左不包右 只有返回值是截取的小段 所以要有返回值
String substring(int beginIndex)截取到末尾
截取手机号的前三位
phoneNumber.substring(0,3);
可是结果打印出来还是这些数字没有去截取
所以这里要看
重点就是要有返回值
String start = phonenumber.substring(0, 3);
System.out.println(start);
下一步就是截取手机号后四位
最后拼接
代码展示
public class StringDemo9 {
public static void main(String[] args) {
//获取一个手机号
String phonenumber="13112349468";
String start = phonenumber.substring(0, 3);
String end = phonenumber.substring(7);
String result =start+"****"+end;
System.out.println(result);
}
}
案例three 身份证信息查看
基本常识
身份证前2位是省份 3,4位是城市5,6位是区县7-14位出生年月日15,16位所在地派出所
17位是性别 基数是男性 偶数是女性 18位是个人信息码随机产生的
案例的要求
是吧身份证信息里面的7-14位提取出来转换成人物信息的出生年月日 第十七位要转换成汉字男女
代码思路
先定义一个字符串记录身份证号码
再用上个案例的截取把生日和性别截取出来
String substring(int beginIndex,int endIndex)
截取索引
注意点:包头不包尾 包左不包右 只有返回值是截取的小段 所以要有返回值
String substring(int beginIndex)截取到末尾
charAt获取单个索引
获取性别的时候除了用截取id.substring还可以使用charAt去获取单个索引
然后获取的性别是字符 要把字符转换成数字才可以进行下一步取余
利用ascii表进行转换
‘0’====》48
‘1’====》49
‘2’====》50
........
这边正好去用‘2’减去‘0’就是他们的差值刚好是2 所以我们可以用gender去减去48看他们相差多少
紧接着对性别数字进行奇偶分辨
代码展示
public class StringDemo10 {
public static void main(String[] args) {
String id="321281202001011234";
String year = id.substring(6, 10);
String month = id.substring(10, 12);
String day = id.substring(12, 14);
System.out.println("出生年月日:"+year+"年"+day+"日");
char gender = id.charAt(16);
int num=gender-48;
if (num%2==0){
System.out.println("女");
}else {
System.out.println("男");
}
}
}
案例four 敏感词替换
小故事
如果那天我说的不好听的话都变成**** 那可能我的号不会被封
这个案例就是检测敏感词替换
String replace(旧值,新值)替换
注意点:只有返回值才是替换之后的结果
代码思路
首先先获取到说的话
然后把敏感词替换了talk.replace
这种比较简单 我们接着定义一个敏感词库
String【】 arr={“”}
然后去用for循环包围
代码展示
public class StringDemo11 {
public static void main(String[] args) {
String talk="你玩的真好,以后不要玩了,TMD,CNM";
String[] arr={"TMD","CNM","SB","MLGB"};
for (int i=0;i< arr.length;i++) {
talk = talk.replace(arr[i], "***");
}
System.out.println(talk);
}
}
StringBuilder
概述:
StringBuilder可以看成一个容器,创建之后里面的内容是可变的
作用:
提高字符串的操作效率
普通字符串拼接
正常字符串拼接的话拼接s1--5是先把s1和s2拼接好 再用s1 s2和s3进行拼接 如此反复会产生很多没有用的字符串
StringBuilder只有一个容器 效率更高
StringBuilder的构造方法:
空参构造
public StringBuilder() 创建一个空白可变字符串对象不含有任何内容
有参构造
public StringBuilder(String str)根据字符串的内容,来创建可变字符串对象
StringBuilder的成员方法
public StringBuilder append(任意类型) 添加数据并且返回对象本身
public StringBuilder reverse() 反转容器中的内容 abc可以反转成cba
public int length()返回长度
public String toString() 通过toString就可以实现把StringBuilder转换成String
知识点普及:
StringBuilder是java已经写好的类 java在底层对他做了特殊的处理 打印的对象不是地址值而是属性值
StringBuilder容器中的内容可以直接进行修改 而字符串不可以直接修改需要一个返回值
在StringBuilder反转的时候不需要一个返回值 直接就可以在容器中进行反转
代码展示
public class StringBuilderDemo1
{
public static void main(String[] args) {
//创建对象
StringBuilder sb=new StringBuilder("abc" );
//添加元素
sb.append(1);
sb.append(2.3);
//数据反转
sb.reverse();
//获取长度
int len=sb.length();
System.out.println(len);
System.out.println(sb);
}
}
知识点
再用stringbuilder方法对字符串进行一个拼接的时候 拼接好的字符串是在一个容器中 最后要用tostring方法把他变回来
代码展示
public class StringBuilderDemo2 {
public static void main(String[] args) {
StringBuilder sb=new StringBuilder();
//添加字符串
sb.append("aaa");
sb.append("bbb");
sb.append("ccc");
sb.append("ddd");
System.out.println(sb);
//再用tostring方法变回字符串
String str=sb.toString();
System.out.println(str);
}
}
链式编程:
在我们调用一个方法的时候,不需要用变量接受他的结果,可以调用其他方法
比如在一个方法中返回了一个字符串 我们可以直接使用这个字符串然后去使用字符串其他的方法
在上面的代码中 调用的append方法返回的对象还是Stringbuilder对象 所以可以将代码改为
sb.sppend("aaa").sppend("bbb").sppend("ccc").sppend("ddd")
StringBuilder案例 对称字符串
需求:键盘接受一个字符串,程序判断该字符串是不是对称字符串,并且打印结果
对称字符串:123321 111
代码思路:首先录入字符串 创建一个容器
用链式结构更简单 :第一行代码右边创建对象 左边把右边的地址值赋值给sb对象
我们直接用容器调用append方法把str放进去 最后tostring变回字符串 一行代码搞定
代码展示
import java.util.Scanner;
public class StringBuilderDemo3 {
public static void main(String[] args) {
Scanner sc =new Scanner(System.in);
System.out.println("输入一个字符串:");
String str = sc.next();
//反转键盘录入的字符串
StringBuilder sb=new StringBuilder();
sb.append(str);
sb.reverse();
System.out.println(sb);
}
}
链式结构
//反转键盘录入的字符串
String result = new StringBuilder().append(str).reverse().toString();
System.out.println(result);
import java.util.Scanner;
public class StringBuilderDemo3 {
public static void main(String[] args) {
Scanner sc =new Scanner(System.in);
System.out.println("输入一个字符串:");
String str = sc.next();
//反转键盘录入的字符串
String result = new StringBuilder().append(str).reverse().toString();
if(str.equals(result)){
System.out.println("right");
}else {
System.out.println("no");
}
}
}
使用Stringbuilder的场景
1.字符串的拼接
2.字符串的反转
需求:拼接字符串
例如:数组为int[] arr={1,2,3};
执行方法后的输出结果为:[1,2,3]
之前我们用字符串直接拼接 速度比较慢
代码展示
public class StringBuilderDemo4 {
public static void main(String[] args) {
int[] arr={1,2,3};
//调用方法把数组变成字符串
String str = arrtoString(arr);
System.out.println(str);
}
public static String arrtoString(int[] arr){
StringBuilder sb=new StringBuilder();
sb.append("[");
for (int i = 0; i < arr.length; i++) {
if (i==arr.length-1) {
sb.append(arr[i]);
}else{
sb.append(arr[i]).append(",");
}
}
sb.append("]");
return sb.toString();
}
}
StringJoiner
概述:
可以看成一个容器,创建之后内容可变
作用:
速度快且简洁
StringJoiner的构造方法
public StringJoiner(间隔符号):创建一个StringJoiner对象,指定拼接时的间隔符号
public StringJoiner(间隔符号):创建一个StringJoiner对象,指定拼接时的间隔符号,开始符号,结束符号
StringJoiner的成员方法
public StringJoiner add 添加数据,并返回对象本身***由于他和stringbuilder都可以返回本身所以他们都可以使用链式结构
public int length):返回长度(字符出现的个数)
public String toString() 返回一个字符串(该字符串就是拼接之后的结果)
代码展示
public class StringJoinerDemo1 {
public static void main(String[] args) {
StringJoiner sj=new StringJoiner("---");
sj.add("aaa").add("bbb");
System.out.println(sj);
}
}
StringJoiner sj=new StringJoiner(",","[","]");
length是所有字符的总个数
int len = sj.length();
System.out.println(len);
想变成字符串直接tostring就ok
字符串的原理
扩展底层原理1:字符串存储的内存空间
直接赋值会复用字符串常量池中的 new出来不会复用,而是开辟一个新的空间
扩展底层原理2:==号比较的到底是什么
基本数据类型比较数据值 引用数据类型比较地址值
扩展底层原理3:字符串拼接的底层原理
拼接的时候没有变量,都是字符串,触发字符串的优化机制。在编译的时候就已经是最终的结果了
**
如果有变量参与的话
1.在jdk8之前会用stringbuilder进行拼接
系统底层会自动创建一个stringbuilder对象,然后在调用其append方法完成拼接。拼接后,在调用其同string方法转换成string类型,而tostring方法的底层是直接new了一个字符串对象
刚开始main方法先进栈 在栈里有第一条语句 并且串池里有‘a’ 第二条语句进栈 然后创建一个stringbuilder对象在堆内存里 通过append都放到stringbuilder容器中 最后用tostring方法变回字符串
总体第二条语句就是
new StringBuilder().append(s1).append("b").toString();
第三条代码和上面代码一样
所以说 有一个加号在堆内存中至少会有两个对象 会浪费性能 速度也慢
2.jdk8的时候做了优化
他会先预估一下有多少个对象
系统会预估字符串拼接之后的总大小,把要拼接的内容都放到数组中,此时也是产生了一个新的字符串
总而言之
如果很多字符串变量拼接,不要直接加,在底层会创建多个对象,浪费时间,浪费性能。
扩展底层原理4:StringBuilder提高效率的原理图
先new一个stringbuilder所以会在堆内存中创建一个地址空间 然后挨个把abc放到容器中
常见面试题
问题:下列代码的运行成果是什么?
s1是直接赋值所以他是直接进串池中的
s3 就是有变量的字符串拼接
答案是false
由于s2是没有变量所以会在编译的时候就会将三个相加的拼接为abc 相当于是复用串池中的字符串
扩展底层原理5:StringBuilder源码分析
stringbuilder会默认创建一个长度为16的字节数组
添加的内容小于16直接存
添加的内容大于16会扩容(原来容量的2倍加2)
如果扩容之后还不够,以实际长度为准
再见
字符串的内容我们就几乎都讲完啦
每天我们会有字符串的一些比较难的练习