今天给简析一下String类提供的常用方法中的toCharArray方法。末尾再给一个经典的运用案例。
在JDK1.6的API文档中是这么描述这方法的。toCharArray将此字符串转换为一个新的字符数组并返回一个新分配的字符数组,它的长度是此字符串的长度,它的内容被初始化为包含此字符串表示的字符序列。
举个例子,现在有一个字符串
String str="Hello";
这里,str的长度为5,所以调用toCharArray之后返回一个长度为5的char类型的数组,这里不妨假设这个数组名为chars如下:
char[] chars=str.toCharArray();
在idea中我们打一个断点来看一眼,如下:
这个图能很直观地看到这个chars数组的内容。方法toCharArray就起到了一个这样的作用。
下面给一个这个方法的常见的一个经典案例。通常会结合char的一些特性比如码表之类的来解决一些过滤特殊字符或统计各种字符出现的次数之类的需求。这个具体怎么操作,我们来看一个案例。
给定一个字符串 :Hello2020!!!。过滤掉字符串里面的特殊符号生成一个新字符串并打印到控制台,然后统计大小写字母和数字的出现次数。
我们来分析一下这个需求,我们要过滤字符串里面的特殊符号,我们直接去过滤并不太好操作。我们最后把这个字符串打散成一个个字符再来判断。那怎么判断这个字符是不是属于大小写或者数字呢?这里需要借助一下ASCII码表。先来看一下这个码表。我把大小写字母和数字都给用红框标记了。
先来看看数字怎么判断,如果一个字符,它对应的十进制数在48到57之间,那一定是数字了。我们不妨假设被比较的那个字符叫c,即
char c=chars[i];
字符c对应的十进制数在48到57,即
c>=48 && c<=57
依次类推,字符a对应97,字符z对应122,小写字母的范围就是
c>=97 &7 c<=122
字符A对应的是65,字符Z对应的是90,大写字母的范围就是
c>=65 && c<=90
但是这里如果没有码表,那记住这两个数字确实是个麻烦事情。那数字不如直接就写成字符0到字符9,让java自己去拿到字符对应的十进制数就好了。
为了打消小萌新对这个做法的顾虑,我们还是到idea里面看一眼,这里我们用char类型的c0~c9分别存储了字符0到字符9。然后在debug下面看看里面c0~c9里面存的值,右边红框就是对应的十进制值。显然的字符0对应的是48。那就是说你写字符0和十进制数48的效果是一样的。其他的可以以此类推。
那么,我们就可以把上面的代码改成
c>='0' && c<='9'
以此类推,判断c是不是小写字母就可以改成
c>='a'&&c<='z'
大写字母就可以改成
c>='A' && c<= 'Z'
其余的范围就是属于特殊字符的范围了。至此,我们可以开始我们的过滤过程。但是需求里面还有一个统计大小写字母出现的次数。这里需要统计三个类别的字符的出现次数。我们需要三个计数器。出现的次数一定是整数,不会有某个字符出现半次的情况,所以计数器的数据类型我们设置为整型变量,初值设置为0。这里我们不妨用upperCase来统计大写字母的出现次数,lowerCase来统计小写字母的次数,numbers来统计数字的次数。即:
int upperCase = 0;
int lowerCase = 0;
int numbers = 0;
在我们遍历过滤这个字符串中的每个元素,即遍历由这个字符串用toCharArray生成的字符数组chars时,我们取出的字符落在范围在字符0到字符9则numbers加1,大小写字母以此类推。遍历完数组chars之后,我们就拿到了三种字符各自出现的次数。
最后来看看,生成新的字符串并打印这个需求。打印并没有什么难度,新字符这个需求可以用另外一个String类型的变量来接收,不妨我们把这个变量叫做resultStr。当然这里也可以使用一个StringBuiler类型的变量来接收。只要被取出来的字符是落在大小写字母或者数字,就把这个字符追加到resultStr中。如果说有什么区别的话,String类型的追加用的是加号而StringBuilder类型追加需要用到append方法。
现在我们可以开始写我们的代码。我们不妨假设这个类的名字为Demo。这个类是需要运行的,所以必须带一个主方法main。那我们先写下这个Java类。
public class Demo {
public static void main(String[] args) {
}
}
接下来,我们用一个字符串类型的变量str来存储我们要过滤的字符串,并用toCharArray方法把这个字符串变成char类型的数组,我们不妨给这个数组取名叫chars。
public class Demo {
public static void main(String[] args) {
String str = "Hello2020!!!";
//将字符串转成char[]
char[] chars = str.toCharArray();
}
}
我们解决这个需求的基础就是完成遍历和判断,那我们不妨先来完成这部分代码。再来补充其他的代码。现在我们开始对这个数组做遍历来取出里面的每个字符,这里为了方便叙述,我们不妨把这个被取出的元素叫做c
public class Demo {
public static void main(String[] args) {
String str = "Hello2020!!!";
//将字符串转成char[]
char[] chars = str.toCharArray();
for (int i = 0; i < chars.length; i++) {
//为了方便后续的代码书写,把取出的元素存在c中
char c = chars[i];
}
}
}
然后来判断它是属于哪种字符。
public class Demo {
public static void main(String[] args) {
String str = "Hello2020!!!";
//将字符串转成char[]
char[] chars = str.toCharArray();
for (int i = 0; i < chars.length; i++) {
//为了方便后续的代码书写,把取出的元素存在c中
char c = chars[i];
if (c >= '0' && c <= '9') {
//数字
} else if (c >= 'a' && c <= 'z') {
//小写字母
} else if (c >= 'A' && c <= 'Z') {
//大写字母
}
}
}
}
至此,遍历和判断都完成了。我们先来完成要打印的新字符resultStr的需求。先在for循环外面定义一个String类型的变量resultStr,当取出来的字符落在大小写和数字范围内时做一下字符的拼接。并在for循环外面打印一下结果。
public class Demo {
public static void main(String[] args) {
String str = "Hello2020!!!";
//将字符串转成char[]
char[] chars = str.toCharArray();
//用来接收符合条件的字符的新字符串,用于打印结果
String resultStr = "";
for (int i = 0; i < chars.length; i++) {
//为了方便后续的代码书写,把取出的元素存在c中
char c = chars[i];
if (c >= '0' && c <= '9') {
//数字
//拼接
resultStr += c;
} else if (c >= 'a' && c <= 'z') {
//小写字母
//拼接
resultStr += c;
} else if (c >= 'A' && c <= 'Z') {
//大写字母
//拼接
resultStr += c;
}
}
}
}
打印结果
完成了拼接的需求,我们再来完成统计字符串的需求。如果取出的字符落在字符0到字符9的范围内,统计数字的变量numbers就要进行加一。大小写字母以此类推。修改代码如下:
public class Demo {
public static void main(String[] args) {
String str = "Hello2020!!!";
//将字符串转成char[]
char[] chars = str.toCharArray();
//用来接收符合条件的字符的新字符串,用于打印结果
String resultStr = "";
//统计大写字母
int upperCase = 0;
//统计小写字母
int lowerCase = 0;
//统计数字
int numbers = 0;
for (int i = 0; i < chars.length; i++) {
//为了方便后续的代码书写,把取出的元素存在c中
char c = chars[i];
if (c >= '0' && c <= '9') {
//数字
//拼接
resultStr += c;
//数字出现次数+1
numbers++;
} else if (c >= 'a' && c <= 'z') {
//小写字母
//拼接
resultStr += c;
//小写字母出现次数+1
lowerCase++;
} else if (c >= 'A' && c <= 'Z') {
//大写字母
//拼接
resultStr += c;
//大写字母出现次数+1
upperCase++;
}
}
//打印拼接结果
System.out.println("过滤后的新字符串:" + resultStr);
//打印统计结果
System.out.println("数字出现次数:" + numbers);
System.out.println("大写字母出现次数:" + upperCase);
System.out.println("小写字母出现次数:" + lowerCase);
}
}
运行一下:
至此,这两个需求都完成了。
最后我们再来回顾一下,toCharArray方法。这个方法完成了从字符串到字符类型的数组的转变。数组长度取决于字符串的长度,经常被用于这种过滤特殊字符或者统计某种类型出现次数的场景。这种场景判断关键在于结合码表和char类型数据的特点。萌新容易犯错的地方有两个,一个是将字符0和字符9写成了数字0和数字9,另外一个是没有注意到大写字母和小写字母中间有几个特殊符号。它们并不是连贯的,如下图示: