Java 时间与日期,包装类,正则表达式
一、时间与日期
1. Date
Date 类概述
- Date 类代表当前所在系统的日期时间信息。
Date 的构造器
| 名称 | 说明 |
|---|---|
Java 时间与日期处理涉及 Date、SimpleDateFormat 和 Calendar 类的使用与转换。包装类提供基本类型对应的引用类型支持自动装箱拆箱及字符串转换。正则表达式用于校验数据格式如手机号邮箱,并支持替换分割操作。Arrays 工具类提供数组排序搜索功能,结合 Comparator 实现自定义规则。常见排序算法包括冒泡、选择及二分查找。Lambda 表达式简化函数式接口匿名内部类写法,提升代码简洁性。
Date 类概述
Date 的构造器
| 名称 | 说明 |
|---|---|
| public Date() |
| 创建一个 Date 对象,代表的是系统当前此刻日期时间。 |
Date 的常用方法
| 名称 | 说明 |
|---|---|
| public long getTime() | 返回从 1970 年 1 月 1 日 00:00:00 走到此刻的总的毫秒数 |
案例
/** 学会使用 Date 类处理时间,获取时间的信息 */
public class DateDemo1 {
public static void main(String[] args) {
// 1. 创建一个 Date 类的对象,代表系统此时日期时间对象
Date d = new Date();
System.out.println(d);
// 2. 获取时间毫秒值
long time = d.getTime();
System.out.println(time);
// long time1 = System.currentTimeMillis();
// System.out.println(time1);
System.out.println("-------------------");
// 1. 得到当前时间毫秒值
Date d1 = new Date();
System.out.println(d1);
// 2. 当前时间往后走 1 小时 121s
long time2 = d1.getTime();
time2 += (60 * 60 + 121) * 1000;
// 3. 把时间毫秒值转换成对应的日期对象
// Date d2 = new Date(time2);
// System.out.println(d2);
Date d3 = new Date();
d3.setTime(time2);
System.out.println(d3);
}
}
时间毫秒值->日期对象
| 构造器/方法 | 说明 |
|---|---|
| public Date(long time) | 把时间毫秒值转换成 Date 日期对象。 |
| public void setTime(long time) | 设置日期对象的时间为当前时间毫秒值对应的时间 |
构造器
| 构造器 | 说明 |
|---|---|
| public SimpleDateFormat(String pattern) | 创建简单日期格式化对象,并封装格式化的形式信息 |
格式化方法
| 格式化方法 | 说明 |
|---|---|
| public final String format(Date date) | 将日期格式化成日期/时间字符串 |
| public final String format(Object time) | 将时间毫秒值式化成日期/时间字符串 |
SimpleDateFormat 解析字符串时间成为日期对象
| 解析方法 | 说明 |
|---|---|
| public Date parse(String source) | 从给定字符串的开始解析文本以生成日期 |
public class SimpleDateFormatDemo1 {
public static void main(String[] args) {
// 1. 日期对象
Date d = new Date();
System.out.println(d);
// 2. 格式化这个日期对象
SimpleDateFormat sdf = new SimpleDateFormat("yyyy 年 MM 月 dd 日 HH:mm:ss EEE a");
// 3. 开始格式化日期对象成为喜欢的字符串形式
String rs = sdf.format(d);
System.out.println(rs);
System.out.println("--------------------");
// 4. 格式化时间毫秒值
// 121 秒后的时间毫秒值是多少
long time = d.getTime() + 121 * 1000;
String rs1 = sdf.format(time);
System.out.println(rs1);
}
}
public class SimpleDateFormatDemo2 {
public static void main(String[] args) throws ParseException {
// 目标:学会使用 SimpleDateFormat 解析字符串时间成为日期对象
// 有一个时间 2021 年 08 月 06 日 11:11:11 往后 2 天 14 小时 49 分 04 秒的时间是多少
// 1. 把字符串时间拿到程序中来
String dateStr = "2021 年 08 月 06 日 11:11:11";
// 2. 把字符串时间解析成日期对象:形式必须与被解析时间的形式完全一样,否则运行时解析报错
SimpleDateFormat sdf = new SimpleDateFormat("yyyy 年 MM 月 dd 日 HH:mm:ss");
Date d = sdf.parse(dateStr);
// 3. 完后走 2 天 14 小时 49 分钟 06 秒
long time = d.getTime() + (2L * 24 * 60 * 60 + 14 * 60 * 60 + 49 * 60 + 6) * 1000;
// 4. 格式化这个时间毫秒值得到结果
System.out.println(sdf.format(time));
}
}
练习:
public class SimpleDateFormatTest1 {
public static void main(String[] args) throws ParseException {
// 1. 开始和结束的时间 小皮和小贾
String startTime = "2021-11-11 00:00:00";
String endTime = "2021-11-11 00:10:00";
String xiaoJia = "2021-11-11 00:03:47";
String xiaoPi = "2021-11-11 00:10:11";
// 2. 解析他们的时间
SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");
Date d1 = sdf.parse(startTime);
Date d2 = sdf.parse(endTime);
Date d3 = sdf.parse(xiaoJia);
Date d4 = sdf.parse(xiaoPi);
if (d3.after(d1) && d3.before(d2)) {
System.out.println("小贾秒杀成功,可以发货了!");
} else {
System.out.println("小贾秒杀失败!");
}
if (d4.after(d1) && d4.before(d2)) {
System.out.println("小皮秒杀成功,可以发货了!");
} else {
System.out.println("小皮秒杀失败!");
}
}
}
Calendar 日历类创建日历对象的方法:
| 方法名 | 说明 |
|---|---|
| public static Calendar getInstance() | 获取当前日历对象 |
Calendar 常用方法
| 方法名 | 说明 |
|---|---|
| public int get(int field) | 取日期中的某个字段信息。 |
| public void set(int field, int value) | 修改日历的某个字段信息。 |
| public void add(int field, int amount) | 为某个字段增加/减少指定的值 |
| public final Date getTime() | 拿到此刻日期对象。 |
| public long getTimeInMillis() | 拿到此刻时间毫秒值 |
注意: Calendar 是可变日期对象,一旦修改后其对象本身表示的时间将产生变化。
public class CalendarDemo1 {
public static void main(String[] args) {
// 1. 拿到系统此时日历对象
Calendar cal = Calendar.getInstance();
System.out.println(cal);
// 2. 获取日历的信息:public int get(int field); 取日期中的谋个字段信息
int year = cal.get(Calendar.YEAR);
System.out.println(year);
// 3. public void add(int field, int amount); 为某个字段增加/减少指定的值
cal.add(Calendar.DAY_OF_YEAR, 64);
cal.add(Calendar.MINUTE, 59);
System.out.println(cal);
// 4. public final Date getTime(); 拿到此时日期对象
Date d = cal.getTime();
System.out.println(d);
}
}
| 基本数据类型 | 引用数据类型 |
|---|---|
| byte | Byte |
| short | Short |
| int | Integer |
| long | Long |
| char | Character |
| float | Float |
| double | Double |
| boolean | Boolean |
自动装箱:基本类型的数据和变量可以直接赋值给包装类型的变量。 自动拆箱:包装类型的变量可以直接赋值给基本数据类型的变量。
包装类的特有功能
字符串对象提供了匹配正则表达式的方法
public boolean matches(String regex): 判断是否匹配正则表达式,匹配返回 true,不匹配返回 falsepublic class RegexDemo {
public static void main(String[] args) {
// 校验 手机号码 邮箱 电话号码
//checkPhone();
//checkEmail();
checkTell();
}
public static void checkTell() {
Scanner sc = new Scanner(System.in);
while (true) {
System.out.println("请输入您的电话号码:");
String phone = sc.next();
// 判断电话号码的格式是否正确
if (phone.matches("0\d{2,6}-?\d{5,20}")) {
System.out.println("电话号码格式正确,注册完成!");
break;
} else {
System.out.println("格式错误,请重新输入~~~");
}
}
}
public static void checkEmail() {
Scanner sc = new Scanner(System.in);
while (true) {
System.out.println("请输入您的注册邮箱:");
String phone = sc.next();
// 判断邮箱的格式是否正确
if (phone.matches("\w{1,30}@[a-zA-Z0-9]{2,20}(\.[a-zA-Z0-9]{2,20}){1,2}")) {
System.out.println("邮箱格式正确,注册完成!");
break;
} else {
System.out.println("格式错误,请重新输入~~~");
}
}
}
public static void checkPhone() {
Scanner sc = new Scanner(System.in);
while (true) {
System.out.println("请输入您的手机号码:");
String phone = sc.next();
// 判断手机号码的格式是否正确
if (phone.matches("1[3-9]\d{9}")) {
System.out.println("手机号码格式正确,注册完成!");
break;
} else {
System.out.println("格式错误,请重新输入~~~");
}
}
}
}
| 方法名 | 说明 |
|---|---|
| public String replaceAll(String regex, String newStr) | 按照正则表达式匹配的内容进行替换 |
| public String[] split(String regex) | 按照正则表达式匹配的内容进行分割字符串,返回一个字符串数组。 |
/** 正则表达式在方法中的应用。
* public String[] split(String regex) --按照正则表达式匹配的内容进行分割字符串,返回一个字符串数组
* public String replaceAll(String regex, String newStr) --按照正则表达式匹配的内容进行替换
*/
public class RegexDemo1 {
public static void main(String[] args) {
String names = "刘备 adjoajd 张飞 ajdiajd 关羽 aafjaijnoa";
String[] arrs = names.split("\w+");
for (int i = 0; i < arrs.length; i++) {
System.out.println(arrs[i]);
}
String names2 = names.replaceAll("\w+", " ");
System.out.println(names2);
}
}
Arrays 类的常用 API
| 方法名 | 说明 |
|---|---|
| public static String toString(类型[] a) | 返回数组的内容(字符串形式) |
| public static void sort(类型[] a) | 对数组进行默认升序排序 |
| public static void sort(类型[] a, Comparator<? super T> c) | 使用比较器对象自定义排序 |
| public static int binarySearch(int[] a, int key) | 二分搜索数组中的数据,存在返回索引,不存在返回 -1 |
Arrays 类的排序方法
| 方法名 | 说明 |
|---|---|
| public static void sort(类型[] a) | 对数组进行默认升序排序 |
| public static void sort(类型[] a, Comparator<? super T> c) | 使用比较器对象自定义排序 |
自定义排序规则
冒泡排序的思想
实现冒泡排序的关键步骤分析
选择排序的思想
选择排序的关键
/** 使用选择排序的方法对数组进行排序 */
public class Test1 {
public static void main(String[] args) {
// 1. 定义数组
int[] arr = {5, 3, 6, 8}; // 0 1 2 3
// 2. 定义一个循环控制选择几轮:arr.length - 1
for (int i = 0; i < arr.length - 1; i++) {
// 3. 定义内部循环:控制选择几次
for (int j = i + 1; j < arr.length; j++) {
// 当前位置:arr[i]
// 如果有比当前位置数据更小,则交换
if (arr[i] > arr[j]) {
int temp = arr[i];
arr[i] = arr[j];
arr[j] = temp;
}
}
}
System.out.println(Arrays.toString(arr));
}
}
结论:二分查找正常的检索条件应该是开始位置 min <= 结束位置 max
Lambda 表达式是 JDK 8 开始后的一种新语法形式。
作用:简化匿名内部类的代码写法。
Lambda 表达式的简化格式
(匿名内部类被重写方法的形参列表) -> {
被重写方法的方法体代码。
}
注:-> 是语法形式,无实际含义
注意:Lambda 表达式只能简化函数式接口的匿名内部类的写法形式
函数式接口:首先必须是接口、其次接口中有且仅有一个抽象方法的形式
public class LambdaDemo1 {
public static void main(String[] args) {
// 使用 Lambda 的标准格式简化匿名内部类的代码形式
// Lambda 只能简化接口中只有一个抽象方法的匿名内部类形式
// Swimming s1 = new Swimming() {
// @Override
// public void swim() {
// System.out.println("老师游泳贼快~~~");
// }
// };
// go(s1);
//go(() ->System.out.println("老师游泳贼快~~~"));
go(() -> System.out.println("老师游泳贼快~~~")); //最终简化形式
}
public static void go(Swimming s) {
System.out.println("开始~~~");
s.swim();
System.out.println("结束!!!");
}
}
@FunctionalInterface
interface Swimming {
void swim();
}
public class LambdaDemo2 {
public static void main(String[] args) {
Integer[] ages = {34, 12, 42, 23};
/**
* 参数一:被排序的数组,必须是引用类型的元素
* 参数二:匿名内部类对象,代表了一个比较器对象
*/
// Arrays.sort(ages, new Comparator() {
// @Override
// public int compare(Integer o1, Integer o2) {
// return o1 - o2;//升序
// }
// });
// Arrays.sort(ages, (o1, o2) -> {
// return o1 - o2;//升序
// });
Arrays.sort(ages, (o1, o2) -> o1 - o2); //最终简化形式
System.out.println(Arrays.toString(ages));
}
}

微信公众号「极客日志」,在微信中扫描左侧二维码关注。展示文案:极客日志 zeeklog
查找任何按下的键的javascript键代码、代码、位置和修饰符。 在线工具,Keycode 信息在线工具,online
JavaScript 字符串转义/反转义;Java 风格 \uXXXX(Native2Ascii)编码与解码。 在线工具,Escape 与 Native 编解码在线工具,online
使用 Prettier 在浏览器内格式化 JavaScript 或 HTML 片段。 在线工具,JavaScript / HTML 格式化在线工具,online
Terser 压缩、变量名混淆,或 javascript-obfuscator 高强度混淆(体积会增大)。 在线工具,JavaScript 压缩与混淆在线工具,online
使用加密算法(如AES、TripleDES、Rabbit或RC4)加密和解密文本明文。 在线工具,加密/解密文本在线工具,online
将字符串编码和解码为其 Base64 格式表示形式即可。 在线工具,Base64 字符串编码/解码在线工具,online