第五章:API_常用类2
6.String类
1.构造方法,编码,解码
/*
* 字符串就是由多个字符组成的一串数据的字符串 常量 ,在改变值时会创建一个新的对象。
* */
/*
*构造方法,编码,解码
* */
public class StringDemo0 {
public static void main(String[] args) throws UnsupportedEncodingException {
String s0 = new String();// 调用无参构造方法,将value值赋给char,转为一个空格字符
System.out.println(s0);
String s1 = new String("123");// 将指定字符赋给value
System.out.println(s1);
char [] c = {'a','b','c'};
String s2 = new String(c);// 将char类型数组转为字符串
System.out.println(s2);
String s3 = "abc";
byte [] b0 = s3.getBytes();// 将字符串转换为字节数组,这个过程称作编码
byte [] b1 = s3.getBytes("utf-8");// 指定编码表编码,使用这个的时候需要抛出异常
new String(b0);// 把看不懂的byte数组转为字符, 叫做解码
new String(b1,"utf-8");// 指定编码表解码
new String(b1,0,3,"utf-8");// 指定编码长度
}
}
2.判断功能
/*
* 判断功能
* */
public class StringDemo1 {
public static void main(String[] args) {
// equals 基本上所有的类都重写了Object中的equals方法
String s0 = new String("123");
String s1 = new String("123");
System.out.println(s0 == s1);// false 比较对象,对象不同
System.out.println(s0.equals(s1));// ture 比较内容,内容相同
// 也是比较内容,compareTo方法也已经被String类重写了。
System.out.println(s0.compareTo(s1));
// 相等为 0,不同为负数
System.out.println(s0.contains("1"));// 是否包含指定字符串
String s2 = null;// 这是地址为空,这个字符串不存在
String s3 = "";// 这是空串,内容为空
System.out.println(s0.isEmpty());// 检测是否为空,这里的是判断是否为空串, 不空false
System.out.println(s3.isEmpty());// 检测是否为空,这里的是判断是否为空串, 空为ture
String s4 = "abC";
String s5 = "aBc";
System.out.println(s4.equalsIgnoreCase(s5));// 不区分大小写的比较,这里是ture
System.out.println(s4.startsWith("a"));// 是否以指定字符串开头
System.out.println(s5.endsWith("c"));// 是否以指定字符串结尾
}
}
3.获取功能
/*
* 获取功能:即通过某些方法从字符串中获取某些元素
* */
public class StringDemo2 {
public static void main(String[] args) {
String s0 = "abcdcszc";
// 01234567
System.out.println(s0.length());// 获取字符串长度,其实在底层获取的是数组的长度
System.out.println(s0.charAt(3));// 获取指定索引的字符。
System.out.println(s0.indexOf("c"));// 获得字符首次出现的位置
// 如果需要遍历多个重复字符
System.out.println(s0.indexOf("c",s0.indexOf("c")+1));
System.out.println(s0.lastIndexOf("c"));// 获得字符首次出现的位置, 从后往前
System.out.println(s0.substring(3));// 从指定位置截取截取字符串到结束,返回一个新的字符串,原来的不变。
System.out.println(s0.substring(3,6));// 区间截取,但是开始索引包含,结束索引不包含。
}
}
4.转换功能
/*
* 转换功能
* */
public class StringDemo3 {
public static void main(String[] args) {
char [] c = "abcd".toCharArray();// 把字符串转换为字符数组
System.out.println(Arrays.toString(c));// [a, b, c, d]
String s0 = new String(c);// 通过构造方法将字符数组转换为字符串
String s1 = String.valueOf(c);// 也是将字符数组转换为字符串,底层用的还是String的构造方法
System.out.println(s1);// abcd
String s2 = "abcDEF";
System.out.println(s2.toLowerCase());// 全部转为小写字母 abcdef
System.out.println(s2.toUpperCase());// 全部转为大写字母 ABCDEF
String s3 = s2.concat("aaa");// 将两个字符串连接在一起,一次只能连接两个,并返回一个新的字符串
String s4 = s2+"aa"+"bb"+"cc";// 这个也是字符串连接,可以多个一起连接,但是和上面的还是有一些区别
String s5 = "ab:c:d:ef";
String [] s6 = s5.split(":");// 用正则表达式将字符串分割为字符数组
// 这个符号可以替换,但是有的不能用,例如:|
System.out.println(Arrays.toString(s6));// [ab, c, d, ef]
}
}
5.替换功能
/*
* 替换功能
* */
public class StringDemo4 {
public static void main(String[] args) {
String s0 = "abcdefghik";
System.out.println(s0.replace("c","C"));// 替换,前面是被替换的
String s1 = " abcd ";
System.out.println(s1.length());// 长度为7,前面有三个空格
int a = s1.trim().length();// trim方法可以消除空格,但是不能消除中间的空格。
// 并且这是一个链式调用,得到的是消除空格之后的新字符串的长度
System.out.println(a);
}
}
6.正则表达式(规则表达式)
Regular Expression ,在代码中常简写为 regex, regexp,或者 RE
模式匹配语法:用特定的符号来表示某种规则,去匹配某个字符串。如果字符串与规则相匹配返回true,否则返回false。
概述:字符串是由多个字符串组成的一串数据(字符序列)的字符串常量,值改变后会重新创建一个新的对象。
符号 | 含义 |
---|---|
\\d | 匹配一个[0-9]数字 |
\\D | 匹配一个非数字字符 |
[3,5,7];[357] | 匹配这三个中的任意一个 |
? | 一次或一次也没有 |
* | 零次或多次 |
+ | 一次或多次 |
{n} | 至少n个 |
{n,m} | 至少n个,最多m个 |
\\s | 匹配一个空格字符(空白字符) |
\\S | 匹配一个非空格字符 |
[a-z] | 匹配一个小写字母 |
[A-Z] | 匹配一个大写字母 |
[A-z] | 匹配一个大写或小写字母 |
[a-zA-Z] | 匹配一个大写或小写字母 |
\\w | 匹配大小写字母,下划线,数字 |
\\W | 除了上面的👆 |
\\. | 预定义字符,表示任意字符,使用时需要转义 |
7.StringBuffer类
概述:如果我们对字符串进行操作,每次拼接,都会创建一个新的String对象,即耗时,又浪费空间。而StringBuffer就可以解决这个问题,它是线程安全的可变字符串。StringBuffer声明创建只能使用构造方法,有参,无参都行。
在操作StringBuffer对象时,除了使用 substring()方法时,会创建一个新对象,而旧的不变。其余操作都不会创建新对象。(在底层返回的是this,所以不会创建新对象。)
StringBuffer的默认长度为16。
/*
* StringBuffer(线程安全的可变字符序列): 值可变,除了截取操作之外,不会创建新的对象,节省时间,节约空间。
* */
public class StringBufferDemo {
public static void main(String[] args) {
// StringBuffer 声明创建的时候必须通过构造方法来完成
StringBuffer s0 = new StringBuffer();// 无参构造方法,声明创建 s0 对象
StringBuffer s1 = new StringBuffer("abc");// 有参构造方法,声明创建 s1 对象并赋值
//并且通过底层的方法可以看到 StringBuffer 默认容量为 16,如果有内容,那就是内容长度加上16.
// 添加
s1.append(1);// 向末尾添加,不会创建新的对象
s1.append("def");
System.out.println(s1);// abc1def
// 插入
System.out.println(s1.insert( 2,"A"));// 向指定位置添加字符
// 删除
System.out.println(s1.deleteCharAt(3));// 删除指定位置的字符
System.out.println(s1.delete(2,4));// 删除指定区间的字符, 包含开始,不包含结束
// 替换
System.out.println(s1.replace(0,4,"ABCDE"));// 替换指定位置的字符,包含开始,不包含结束
System.out.println(s1.reverse());// 逆序
// 截取
System.out.println(s1.substring(1,5));// 截取时创建新的字符串对象,原字符串不变。
// 如果不创建就意味着和删除相同。
}
}
8.StringBuilder类
这个类和StringBuffer类的操作基本一样,除了StringBuilder类不是多线程安全的。
/*
* StringBuilder 的操作与 StringBuffer基本一致,因为它们在底层中继承的是同一个父类。
* */
public class StringBuilderDemo {
public static void main(String[] args) {
StringBuilder s = new StringBuilder();
s.append(1);// 向末尾添加
s.insert(2,"A");// 向指定位置插入字符
s.deleteCharAt(0);// 删除指定位置字符
s.delete(0,4);// 删除指定区间字符
s.replace(2,4,"AB");// 替换指定区间字符
s.reverse();// 逆序
s.substring(2,5);// 截取指定区间字符,创建新的对象,原对象不变
}
}
三者区别
String: 是字符常量, 值不可变。适用于少量的字符串操作的情况。
StringBufffer: 值可变 ,除了截取操作之外不会创建新的对象, 多线程安全 ,并且方法加了锁。适用于多线程下在字符缓冲区进行大量操作的情况。
StringBuilder: 和StringBuffer一模一样,但是方法没加锁,多线程可能不安全。它适用于单线程下在字符缓冲区进行大量操作的情况。
9.Math类
java.lang.Math
Math类主要是提供一些静态方法用于科学计算。
因此在使用的时候先导包,具体的使用的时候通过Math类的类名来调用具体方法。
Math类方法的参数和返回值类型一般为double类型。
1.abs绝对值
// abs 求绝对值
// 参数类型可以是 int, long, float, double
// 接收参数也只能是 int, long, float, double
int i = -3;
int a = Math.abs(i);
System.out.println(a);
2.sqrt方法求平方根
// sqrt方法求平方根
// 参数类型可以是整数型,和浮点型
// 参数为正时,正常输出
// 参数为负时,输出NaN
// NaN是javascript的数值类型 Number类型
// NaN意为结果不是一个数字,即就是输出的数值类型系统难以判断,但是没有报错,而是返回了NaN
// NaN 是一个特殊的数值类型,它不会和任何一个值相等,包括它本身
// 0/0也会出现NaN
// sqrt方法的接收类型只能是 double型
float i0 = 3;
double b = Math.sqrt(i0);
System.out.println(b);
3.pow方法求 a 的 b 次幂
// a 的 b 次幂
// 参数类型可以是整数型,和浮点型
// 接收类型只能是 double型
int a1 = 2;
int a2 = -3;
double a3 = Math.pow(a1,a2);
System.out.println(a3);
4.max方法,求两个数中较大的那个
// max方法,求两个数中较大的那个
// 参数类型可以是整数型,和浮点型
// 接收类型的容量只要大于参数类型就可以
int b1 = 3;
float b2 = 8;
double b3 = Math.max(b1,b2);
System.out.println(b3);
5.min方法,求两个数中较小的那个
// min方法,求两个数中较小的那个
// 参数类型可以是整数型,和浮点型
// 接收类型的容量只要大于参数类型就可以
double c = Math.min(b1,b2);
System.out.println(c);
6.random方法,随机一个 (0.0,1.0] 的浮点数
// random方法,随机一个 0.0 —— 1.0 的浮点数
// 它并不是一个 0.2, 0.3这样的浮点数,而是 0.948247884274 这样的数
double c1 = Math.random();
System.out.println("随机数"+c1);
7.round方法,将一个 double 或者 float 数值转为long型,小数部分四舍五入
// round方法,将一个 double 或者 float 数值转为long型,小数部分四舍五入
double c2 = 8.3183781;
double c3 = 3.89939;
float c4 = 3.879f;
long c5 = Math.round(c2);
System.out.println(c5);
long c6 = Math.round(c3);
System.out.println(c6);
long c7 = Math.round(c3);
System.out.println(c7);
8.ceil方法,向上取整
// 参数可以是 float,double
// 接收类型只能是double
double d1 = Math.ceil(8.123);
double d2 = Math.ceil(7.8);
System.out.println("8.123向上取整:"+d1);
System.out.println("7.8向上取整:"+d2);
9.floor方法,向下取整
// 参数可以是 float,double
// 接收类型只能是double
double d3 = Math.floor(5.1231);
double d4 = Math.floor(6.9);
System.out.println("5.1231向下取整:"+d3);
System.out.println("6.9向下取整:"+d4);
10.Random类
这个类是伪随机,即就是有规律的随机
在进行随机时,随机算法的起源数字称为种子数(seed),在种子数的基础上进行一定的变换,从而产生随机数字。
并且相同种子数的Random对象,相同批次产生的随机数完全相同。
也就是说,只要种子数相同,那么两个对象每一次产生两个的随机数都完全相同
1.构造方法
-
无参构造方法
// 无参构造方法 // 该构造方法使用一个和当前系统时间对应的相对时间有关的数字作为种子数,然后使用这个种子数构造Random对象 // 可返回的类型有 int, long, float, double, boolean Random r = new Random(); System.out.println(r.nextBoolean());
-
有参构造方法
// 有参构造方法 // 手动赋值一个种子数,这个种子数只是一个起源数字,跟随机出来的随机数的区间没有任何关系。 // 相同种子数的Random对象相同批次产生的随机数相同 // 同一个对象的同一个种子,第一次的随机数序列和第二次的随机数序列结果一样。 Random r1 =new Random(5); // 7,4,1,9,43,3 // 7,4,1,9,43,3 Random r2 =new Random(5); System.out.println("种子数5::"+r1.nextDouble()); System.out.println("种子数5::"+r2.nextDouble());
2.成员方法
-
无参成员方法
// public int nextInt() // 这个方法产生的随机数没有范围的限制 // 产生的随机数本质上是 int型,因此只要是比 int型容量大的数值类型都可以接收 Random r4 = new Random(); float d1 = r4.nextInt(); System.out.println(d1);
-
有参构造方法
// public int nextInt(int n) // 这个相对于上面的那个,有了界限, // double d2 = r4.nextInt(-1); 参数如果是负数,编译不出错,运行时就会报错。 // java.lang.IllegalArgumentException // 表示方法通过了非法或者不正确的参数 // 参数也不能是小数,直接编译报错 // 接收类型只要比 int型容量大,就可以接收 // bound 表示范围,界限, // 在这里,例如我输入一个 3,那么就只会随机 0, 1, 2. 这也表明了它是不会包括你规定的界限的。 // (0,n] 正整数 double d2 = r4.nextInt(1); System.out.println(d2);
11.System类
System类代表系统,系统级的很多属性和控制方法都放置在该类中。该类位于java.lang包。并且System类不能被实例化。
System类中包含了in(标准输入流:键盘输入),out(标准输出流:显示器),err(标准错误输出流:显示器)三个成员变量。
System.arraycopy( a, srcpos, b, destpos, a.length)
a:源数组 srcpos:源数组起始位置 b:目标数组 destpos:目标数组起始位置 a.length:a数组的长度
System.currentTimeMillis( );返回毫秒级 当前至1970年1月1日0分0秒程序运行的那一刻。
/*
* System类
* */
public class SystemDemo1 {
public static void main(String[] args) {
// System.out; PrintStream 打印流
// System.in; InputStream 输入流
// System.out.println();
// 返回一个不能修改的当前系统环境的字符串映射视图
System.out.println(System.getenv());
// 获取指定的环境变量值
System.out.println(System.getenv("Path"));
// 确定当前的系统属性
System.out.println(System.getProperties());
// System.exit(0); 停止虚拟机
// 返回毫秒级 当前至1970年1月1日0分0秒程序运行的那一刻
System.out.println(System.currentTimeMillis());
// 数组复制
int[] a = {1,2,3,4,7,8,9,10};
int[] b = new int[10];
System.arraycopy(a,2,b,3,4);
/*
* a:源数组
* srcPos: 源数组起始位置(索引)
* b:目标数组
* destPos:目标数组起始位置(索引)
* length:复制的长度
* */
System.out.println(Arrays.toString(b));
}
}
12.Date类
这个类的很多方法现在已经被弃用了,成为了过期方法。
/*
* Date类:目前很多的方法已经弃用,被Calendar类所替代
* 使用时需要引入包
* */
public class DateDemo1 {
public static void main(String[] args) {
Date date = new Date();
// 日期对象中封装了当前时间信息,精确到毫秒
System.out.println(date);
// 返回毫秒级 当前至1970年1月1日0分0秒程序运行的那一刻
System.out.println(System.currentTimeMillis());
// 和上面的一样
long l = date.getTime();
// 将一个long型时间,转换为Date对象。
// 返回的是一个1970年加上你所输入的参数的时间。
Date date1 = new Date(l);
System.out.println(date1);
// 有删除线的就是过期方法,已弃用,不建议使用。
System.out.println(date.getDate());// 这一月的第几天
System.out.println(date.getDay());// 这个星期的第几天
System.out.println(date.getYear()+1900);// 年份
System.out.println(date.getMonth()+1);// 月份,国外的月份是从零开始的
}
}
13.Calendar类(日历类)
关于时间建议使用这个类,这也是一个抽象类,不能实例化。
/*
* Calendar类(日历类),关于时间建议使用这个类;这也是一个抽象类,不能实例化
* 并且使用这个类的时候需要调用
* */
public class CalendarDemo1 {
public static void main(String[] args) {
// 虽然Calendar类不能实例化,但是可以父类引用指向子类对象。
Calendar c = new GregorianCalendar();
// getInstance 这个类方法实际上返回的还是子对象 GregorianCalendar
Calendar c1 = Calendar.getInstance();
// Calendar.YEAR 这是一个给定的日期字段,我们需要通过 get()方法获取给定字段的值。
System.out.println(c.get(Calendar.YEAR));// 2020
// 通过set方法设置给定字段的值。
c.set(1,10);
System.out.println(c.get(Calendar.YEAR));// 10
System.out.println(c.get(Calendar.DAY_OF_WEEK));// 这周的第几天
System.out.println(c1.get(Calendar.DAY_OF_YEAR));// 这年的第几天
System.out.println(c.get(Calendar.MONTH)+1);// 这年的第几个月
}
}
14.SimpleDateFormat类(简单日期格式化类)
主要功能是格式化(日期 --> 文本),解析(文本 --> 日期),和标准化。
在java.text包中
public class SimpleDateFormatDemo {
public static void main(String[] args) throws ParseException {
// 调用构造方法自定义格式
/*
* 模式匹配代码 (注意大小写和数量)
* yyyy 2019年 yy 19年
* MM 09月
* dd 12日
* HH 8时
* mm 18分
* ss 56秒
* SS 378毫秒
* */
// 这也是日期转字符串的过程
SimpleDateFormat s1 = new SimpleDateFormat("yyyy年MM月dd日 HH:mm:ss");
SimpleDateFormat s2 = new SimpleDateFormat("现在是MM月dd日 HH时");
SimpleDateFormat s3 = new SimpleDateFormat("yyyy/MM/dd HH:mm:ss SS");
// 使用 format方法应用自定义格式
System.out.println(s1.format(new Date()));
System.out.println(s2.format(new Date()));
System.out.println(s3.format(new Date()));
// 字符串转日期
// 首先定义日期格式
SimpleDateFormat s4 = new SimpleDateFormat("yyyy/MM/dd HH:mm");
// 按照格式来匹配字符串
String s5 = "2020/11/12 18:53";
// 调用parse方法 , 并且需要抛出异常
Date date = s4.parse(s5);
System.out.println("字符串转日期:"+date);
}
}
15.BigInteger类(大数类)
在java中有许多数字处理的类,但是都有一定的局限性。我们学过的Integer也只是int的包装类,范围是没有变化的。
所以在java中还提供了范围更大的数据类型,它支持任意精度的整数。
BigInteger类位于 java.math包中
public class BigIntegerDemo {
public static void main(String[] args) {
// 构造方法
// 这个构造方法的形参是字符串
// 可以直接将十进制的字符串变为大整数
BigInteger b1 = new BigInteger("123");
BigInteger b2 = new BigInteger("2");
BigInteger b3 = new BigInteger("13");
System.out.println(b1);
// 因为BigInteger不是基本类型,所以就不能再使用 +, -, *, /
// 但是java给它提供了相应的方法
// add() 加
// subtract() 减
// multiply() 乘
// divide() 除
b1 = b2.add(b3);
System.out.println(b1);
b1 = b2.subtract(b3);
System.out.println(b1);
b1 = b2.multiply(b3);
System.out.println(b1);
b1 = b2.divide(b3);
System.out.println(b1);
}
}
16.BigDecimal类
在计算机中存在float, double这样的浮点数,但是计算机是二进制的,浮点数会失去一定的精确度。
根本原因就是: 十进制通常没有完全相同的二进制表示形式;十进制数的二进制表示形式只能无限接近于那个值。
double a = 0.9 - 0.8
a == 0.1 (false)
但是现实生活中我们不能容忍这样的状况存在。
因此有了BigDecimal类
存在于java.math包中
BigDecimal是不可变的,在进行操作之后会创建一个新的对象, 原对象不变。因此一定要注意保留操作后的。
public class BigDecimalDemo {
public static void main(String[] args) {
// 构造方法有三种
// int
BigDecimal b1 = new BigDecimal(1000);
System.out.println(b1);
// double, 这种不建议使用,因为 double 的构造方法的结果有一定的不可预知性
BigDecimal b2 = new BigDecimal(2.3);
System.out.println(b2);
// String,强烈建议优先使用,因为 String 构造方法是完全可预知的
BigDecimal b3 = new BigDecimal("2.1");
System.out.println(b3);
// 如果必须使用 double类型,请通过下面两种方法使用
// BigDecimal中的valueOf()方法
BigDecimal b4 = BigDecimal.valueOf(2.3);
System.out.println(b4);
// Double包装类的 toString()方法转成 String
BigDecimal b5 = new BigDecimal(Double.toString(4.6));
System.out.println(b5);
// add() 加, subtract()减, multiply() 乘, divide() 除。
// System.out.println(b4.divide(b3));
// 这里需要注意除法,如果出现不整除的情况会运行报错。java.lang.ArithmeticException
// 其实divide()方法可以传三个参数。
// 按照顺序:BigDecimal divisor(除数), int scale(保留小数的位数), int roundingMond(舍入模式)
// 舍入模式只在四舍五入时才需要使用
// ROUND_HALF_DOWN 向下舍入 1.55 ——> 1.5
// ROUND_HALF_UP 向上舍入(四舍五入时可以使用) 1.55 --> 1.6
BigDecimal b6 = new BigDecimal("6125");
System.out.println(b6.divide(b1,2,BigDecimal.ROUND_HALF_UP));
System.out.println(b6.divide(BigDecimal.valueOf(1000),3,BigDecimal.ROUND_HALF_DOWN));
System.out.println(b6.divide(BigDecimal.valueOf(1000),BigDecimal.ROUND_HALF_DOWN));
// 需要对BigDecimal 进行截断和四舍五入的时候可以使用 setScale 方法
BigDecimal b7 = new BigDecimal("5.67869");
// 在写入模式的时候有两种语法格式
b7 = b7.setScale(3,BigDecimal.ROUND_HALF_UP);
System.out.println(b7);
b7 = b7.setScale(2, RoundingMode.HALF_UP);
System.out.println(b7);
}
}
若有错误,欢迎私信指正。