1.时间日期类
1.1 Date类
计算机中的时间原点:1970年1月1日 00:00:00。由于我们在东八区,所以我们的时间原点是1970年1月1日 08:00:00。
构造方法:
方法名 | 说明 |
---|---|
public Date() | 分配一个 Date对象,并初始化,以便它代表它被分配的时间,精确到毫秒 |
public Date(long date) | 分配一个 Date对象,并将其初始化为表示从标准基准时间起指定的毫秒数 |
常用方法:
方法名 | 说明 |
---|---|
public long getTime() | 获取的是日期对象从1970年1月1日 08:00:00到现在的毫秒值 |
public void setTime(long time) | 设置时间,给的是毫秒值。 |
1.2 SimpleDateFormat类
概述:SimpleDateFormat是一个具体的类,用于以区域设置敏感的方式格式化和解析日期。
构造方法:
方法名 | 说明 |
---|---|
public SimpleDateFormat() | 构造一个SimpleDateFormat,使用默认模式和日期格式 |
public SimpleDateFormat(String pattern) | 构造一个SimpleDateFormat使用给定的模式和默认的日期格式 |
常用方法:
-
格式化(从Date到String)
public final String format(Date date):将日期格式化成日期/时间字符串 -
解析(从String到Date)
public Date parse(String source):从给定字符串的开始解析文本以生成日期
2. JDK8时间日期类
2.1 JDK8新增日期类
-
LocalDate 表示日期(年月日)
-
LocalTime 表示时间(时分秒)
-
LocalDateTime 表示时间+ 日期 (年月日时分秒)
2.2 LocalDateTime创建方法
方法名 | 说明 |
---|---|
public static LocalDateTime now() | 获取当前系统时间 |
public static LocalDateTime of (年, 月 , 日, 时, 分, 秒) | 使用指定年月日和时分秒初始化一个LocalDateTime对象 |
2.3 LocalDateTime获取方法
方法名 | 说明 |
---|---|
public int getYear() | 获取年 |
public int getMonthValue() | 获取月份(1-12) |
public int getDayOfMonth() | 获取月份中的第几天(1-31) |
public int getDayOfYear() | 获取一年中的第几天(1-366) |
public DayOfWeek getDayOfWeek() | 获取星期 |
public int getMinute() | 获取分钟 |
public int getHour() | 获取小时 |
public int getSecond() | 获取秒 |
2.4 LocalDateTime转换方法
方法名 | 说明 |
---|---|
public LocalDate toLocalDate () | 转换成为一个LocalDate对象 |
public LocalTime toLocalTime () | 转换成为一个LocalTime对象 |
2.5 LocalDateTime格式化和解析 (应用)
方法名 | 说明 |
---|---|
public String format (指定格式) | 把一个LocalDateTime格式化成为一个字符串 |
public LocalDateTime parse (准备解析的字符串, 解析格式) | 把一个日期字符串解析成为一个LocalDateTime对象 |
public static DateTimeFormatter ofPattern(String pattern) | 使用指定的日期模板获取一个日期格式化器DateTimeFormatter对象 |
注:format方法不是静态的,要通过对象名.format(DateTimeFormatter patter)来调用
parse方法是静态的,可以通过LocalDateTime.parse(String s,DateTimeFormatter patter)来调用
public class Demo03 {
public static void main(String[] args) {
//method1();
//method2();
}
private static void method2() {
String s = "1999年02月25日 00:00:00";
DateTimeFormatter pattern = DateTimeFormatter.ofPattern("yyyy年MM月dd日 HH:mm:ss");
LocalDateTime parseTime = LocalDateTime.parse(s, pattern);//parse:String -> LocalDateTime
System.out.println(parseTime);//1999-02-25T00:00
}
private static void method1() {
LocalDateTime nowTime = LocalDateTime.now();
DateTimeFormatter pattern = DateTimeFormatter.ofPattern("yyyy年MM月dd日 HH:mm:ss");
String s = nowTime.format(pattern);//format:LocalDateTime -> String
System.out.println(s);//2021年05月02日 11:06:53
}
}
2.6 LocalDateTime增加或者减少时间的方法
方法名(可以接收正数->往后加,也可以接收负数->往前减) | 说明 |
---|---|
public LocalDateTime plusYears (long years) | 添加或者减去年 |
public LocalDateTime plusMonths(long months) | 添加或者减去月 |
public LocalDateTime plusDays(long days) | 添加或者减去日 |
public LocalDateTime plusHours(long hours) | 添加或者减去时 |
public LocalDateTime plusMinutes(long minutes) | 添加或者减去分 |
public LocalDateTime plusSeconds(long seconds) | 添加或者减去秒 |
public LocalDateTime plusWeeks(long weeks) | 添加或者减去周 |
注:如果改变的值超出了范围,整个时间会相应的按照实际现实改变。
public class Demo04 {
public static void main(String[] args) {
LocalDateTime localDateTime = LocalDateTime.of(2020, 11, 11, 13, 14, 15);
LocalDateTime newLocalDateTime = localDateTime.plusYears(1);
System.out.println(newLocalDateTime);//2021-11-11T13:14:15
LocalDateTime newLocalDateTime1 = localDateTime.plusYears(-1);
System.out.println(newLocalDateTime1);//2019-11-11T13:14:15
//如果改变的值超出了范围,整个时间会相应的按照实际现实改变。
LocalDateTime newLocalDateTime2 = localDateTime.plusMonths(2);
System.out.println(newLocalDateTime2);//2021-01-11T13:14:15
}
}
2.7 LocalDateTime减少或者增加时间的方法
方法名(可以接收正数->往前减,也可以接收负数->往后加) | 说明 |
---|---|
public LocalDateTime minusYears (long years) | 减去或者添加年 |
public LocalDateTime minusMonths(long months) | 减去或者添加月 |
public LocalDateTime minusDays(long days) | 减去或者添加日 |
public LocalDateTime minusHours(long hours) | 减去或者添加时 |
public LocalDateTime minusMinutes(long minutes) | 减去或者添加分 |
public LocalDateTime minusSeconds(long seconds) | 减去或者添加秒 |
public LocalDateTime minusWeeks(long weeks) | 减去或者添加周 |
注:如果改变的值超出了范围,整个时间会相应的按照实际现实改变。
2.8 LocalDateTime修改方法
方法名 | 说明 |
---|---|
public LocalDateTime withYear(int year) | 直接修改年 |
public LocalDateTime withMonth(int month) | 直接修改月 |
public LocalDateTime withDayOfMonth(int dayofmonth) | 直接修改日期(一个月中的第几天) |
public LocalDateTime withDayOfYear(int dayOfYear) | 直接修改日期(一年中的第几天) |
public LocalDateTime withHour(int hour) | 直接修改小时 |
public LocalDateTime withMinute(int minute) | 直接修改分钟 |
public LocalDateTime withSecond(int second) | 直接修改秒 |
public class Demo05 {
public static void main(String[] args) {
LocalDateTime localDateTime = LocalDateTime.of(2020, 11, 11, 13, 14, 15);
LocalDateTime localDateTime1 = localDateTime.withYear(2048);
System.out.println(localDateTime1);//2048-11-11T13:14:15
//注意参数范围
LocalDateTime localDateTime2 = localDateTime.withMonth(20);//DateTimeException
System.out.println(localDateTime2);
}
}
2.9 Period
方法名 | 说明 |
---|---|
public static Period between(开始日期,结束日期) | 计算两个日期的间隔 |
public int getYears() | 获得这段日期的年数 |
public int getMonths() | 获得此期间的总月数 |
public int getDays() | 获得此期间的天数 |
public long toTotalMonths() | 获取此期间的总月数 |
/**
* 计算两个日期的间隔
*/
public class JDK8DateDemo9 {
public static void main(String[] args) {
//public static Period between(开始日期,结束日期) 计算两个日期的间隔
LocalDate localDate1 = LocalDate.of(2020, 1, 1);
LocalDate localDate2 = LocalDate.of(2048, 12, 12);
Period period = Period.between(localDate1, localDate2);
System.out.println(period);//P28Y11M11D
//public int getYears() 获得这段日期的年数
System.out.println(period.getYears());//28
//public int getMonths() 获得此期间的月数
System.out.println(period.getMonths());//11
//public int getDays() 获得此期间的天数
System.out.println(period.getDays());//11
//public long toTotalMonths() 获取此期间的总月数
System.out.println(period.toTotalMonths());//347
}
}
2.10 Duration
方法名 | 说明 |
---|---|
public static Duration between(开始时间,结束时间) | 计算两个“时间"的间隔 |
public long toSeconds() | 获得此时间间隔的秒 |
public int toMillis() | 获得此时间间隔的毫秒 |
public int toNanos() | 获得此时间间隔的纳秒 |
/**
* 计算两个时间的间隔
*/
public class JDK8DateDemo10 {
public static void main(String[] args) {
//public static Duration between(开始时间,结束时间) 计算两个“时间"的间隔
LocalDateTime localDateTime1 = LocalDateTime.of(2020, 1, 1, 13, 14, 15);
LocalDateTime localDateTime2 = LocalDateTime.of(2020, 1, 2, 11, 12, 13);
Duration duration = Duration.between(localDateTime1, localDateTime2);
System.out.println(duration);//PT21H57M58S
//public long toSeconds() 获得此时间间隔的秒
System.out.println(duration.toSeconds());//79078
//public int toMillis() 获得此时间间隔的毫秒
System.out.println(duration.toMillis());//79078000
//public int toNanos() 获得此时间间隔的纳秒
System.out.println(duration.toNanos());//79078000000000
}
}
3.异常
3.1异常
3.2 编译时异常和运行时异常的区别
编译时异常
-
都是Exception类及其子类
-
必须显示处理,否则程序就会发生错误,无法通过编译
运行时异常
-
都是RuntimeException类及其子类
-
无需显示处理,也可以和编译时异常一样处理
3.3 JVM默认处理异常的方式
把异常的名称,错误原因及异常出现的位置等信息输出在控制台。程序停止执行。
3.4 throws方式处理异常
定义格式
public void 方法() throws 异常类名 {
}
public class ExceptionDemo {
public static void main(String[] args) throws ParseException{
System.out.println("开始");
// method();
method2();
System.out.println("结束");
}
//编译时异常
public static void method2() throws ParseException {
String s = "2048-08-09";
SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd");
Date d = sdf.parse(s);
System.out.println(d);
}
//运行时异常
public static void method() throws ArrayIndexOutOfBoundsException {
int[] arr = {1, 2, 3};
System.out.println(arr[3]);
}
}
注:
-
这个throws格式是跟在方法的括号后面的
-
编译时异常必须要进行处理,两种处理方案:try...catch …或者 throws,如果采用 throws 这种方案,在方法上进行显示声明,将来谁调用这个方法谁处理
-
运行时异常因为在运行时才会发生,所以在方法后面可以不写,运行时出现异常默认交给JVM处理
3.5 throw抛出异常
格式:throw new 异常();
注意:这个格式是在方法内的,表示当前代码手动抛出一个异常,下面的代码不再执行
throws和throw的区别:
throws | throw |
---|---|
用在方法声明后面,跟的是异常类名 | 用在方法体内,跟的是异常对象名 |
表示声明异常,调用该方法有可能会出现这样的异常 | 表示手动抛出异常对象,由方法体内的语句处理 |
3.6 try-catch方式处理异常
try {
可能出现异常的代码;
} catch(异常类名 变量名) {
异常的处理代码;
}
执行流程
-
程序从 try 里面的代码开始执行
-
出现异常,就会跳转到对应的 catch 里面去执行
-
执行完毕之后,程序还可以继续往下执行(try...catch后边的语句)
注意
-
如果 try 中没有遇到问题,怎么执行?
会把try中所有的代码全部执行完毕,不会执行catch里面的代码
-
如果 try 中遇到了问题,那么 try 下面的代码还会执行吗?
那么直接跳转到对应的catch语句中,try下面的代码就不会再执行了 当catch里面的语句全部执行完毕,表示整个体系全部执行完全,继续执行下面(try...catch后)的代码
-
如果出现的问题没有被捕获,那么程序如何运行?
那么try...catch就相当于没有写.那么也就是自己没有处理.默认交给虚拟机处理.
-
同时有可能出现多个异常怎么处理?
出现多个异常,那么就写多个catch就可以了. 注意点:如果多个异常之间存在子父类关系.那么父类一定要写在下面.不然后边的catch就捕捉不到了,全被前边的父类捕获到了
3.7 Throwable成员方法
方法名 | 说明 |
---|---|
public String getMessage() | 返回此 throwable 的详细消息字符串 |
public String toString() | 返回此可抛出的简短描述 |
public void printStackTrace() | 把异常的错误信息输出在控制台 |
public class ExceptionDemo02 {
public static void main(String[] args) {
System.out.println("开始");
method();
System.out.println("结束");
}
public static void method() {
try {
int[] arr = {1, 2, 3};
System.out.println(arr[3]); //new ArrayIndexOutOfBoundsException();
System.out.println("这里能够访问到吗");
} catch (ArrayIndexOutOfBoundsException e) { //new ArrayIndexOutOfBoundsException();
// e.printStackTrace();
//public String getMessage():返回此 throwable 的详细消息字符串
// System.out.println(e.getMessage());
//Index 3 out of bounds for length 3
//public String toString():返回此可抛出的简短描述
// System.out.println(e.toString());
//java.lang.ArrayIndexOutOfBoundsException: Index 3 out of bounds for length 3
//public void printStackTrace():把异常的错误信息输出在控制台
e.printStackTrace();
// java.lang.ArrayIndexOutOfBoundsException: Index 3 out of bounds for length 3
// at com.itheima_02.ExceptionDemo02.method(ExceptionDemo02.java:18)
// at com.itheima_02.ExceptionDemo02.main(ExceptionDemo02.java:11)
}
}
}
3.8 自定义异常
概述:当Java中提供的异常不能满足我们的需求时,我们可以自定义异常
步骤:1.创建一个自定义异常类继承Exception或RuntimeException,如果不要求调用者一定要处理抛出的异常,就继承RuntimeException。
2.书写异常类构造方法。一般选择generate自动生成前两个(空参构造和带字符串构造)。
3.在实体类中判断条件后抛出异常throw new XXXException("异常提示信息");
4.在测试类中catch(XXXException e){e.printStackTrace();//输出异常信息}
/*
*自定义异常类
*/
public class AgeOutOfBoundsException extends RuntimeException {
public AgeOutOfBoundsException() {
}
public AgeOutOfBoundsException(String message) {
super(message);
}
}
/*
*学生实体类
*/
public class Student {
private String name;
private int age;
public Student() {
}
public Student(String name, int age) {
this.name = name;
this.age = age;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public int getAge() {
return age;
}
public void setAge(int age) {
if (age >= 18 && age <= 25){
this.age = age;
}else{
throw new AgeOutOfBoundsException("年龄范围错误");
}
}
@Override
public String toString() {
return "Student{" +
"name='" + name + '\'' +
", age=" + age +
'}';
}
}
/*
*测试类
*/
public class Demo02 {
public static void main(String[] args) {
Student s = new Student();
Scanner sc = new Scanner(System.in);
System.out.println("请输入学生姓名:");
String name = sc.next();
s.setName(name);
while(true){
System.out.println("请输入学生年龄:");
String ageStr = sc.next();
try {
int age = Integer.parseInt(ageStr);
s.setAge(age);
break;
} catch (NumberFormatException e) {
System.out.println("请输入一个整数");
}catch (AgeOutOfBoundsException e) {
//e.printStackTrace();
System.out.println("请输入一个符合范围的年龄");
}
}
System.out.println(s.toString());
}
}
/*
*测试结果
*/
请输入学生姓名:
zhangsan
请输入学生年龄:
abc
请输入一个整数
请输入学生年龄:
50
请输入一个符合范围的年龄
请输入学生年龄:
18
Student{name='zhangsan', age=18}