1.ToString()方法
java.lang.Object
类 Object 是类层次结构的根(父)类。
每个类(Person,Student…)都使用 Object 作为超(父)类。
所有对象(包括数组)都实现这个类的方法。
Person类默认继承了Object类,所以可以使用Object类中的toString方法
String toString() 返回该对象的字符串表示(就是直接返回地址)。因为直接打印对象名就是输出地址值(其实就是调用toString),没什么意思,所有我们要在对应的类中重写tostring方法(打印其属性值,idea有对应快捷键)
class Person{
public String name;
public int age;
public Person() {
}
public Person(String name, int age) {
this.name = name;
this.age = age;
}
@Override
public String toString() {
return "Person{" +
"name='" + name + '\'' +
", age=" + age +
'}';
}
}
public class Test {
public static void main(String[] args) {
Person p=new Person("张三",18);
//没重写tostring前
//String s = p.toString();
//System.out.println(s); //Person@75412c2f
//直接打印对象的名字,其实就是调用对象的toString p=p.toString();
//System.out.println(p); //Person@75412c2f
//看一个类是否重写了toString,直接打印这个类的对象即可,如果没有重写toString方法那么打印的是对象的地址值
//重写后:
System.out.println(p);//Person{name='张三', age=18}
}
}
2.equals方法
Person类默认继承了Object类,所以可以使用Object类的equals方法(前面讲的字符串equal方法是重写这个的哦字符串的equal)
boolean equals(Object obj) 指示其他某个对象是否与此对象“相等”。
equals方法源码:
public boolean equals(Object obj) {
return (this == obj);
}
参数:
Object obj:可以传递任意的对象
== 比较运算符,返回的是一个布尔值 true false
基本数据类型:比较的是值
引用数据类型:比价的是两个对象的地址值
this是谁?那个对象调用的方法,方法中的this就是那个对象;p1调用的equals方法所以this就是p1obj是谁?传递过来的参数p2
两个对象直接equal会返回flase,但p1=p2(把p2的地址给p1就相等了)
eg:
class Person{
public String name;
public int age;
public Person() {
}
public Person(String name, int age) {
this.name = name;
this.age = age;
}
// @Override
// public String toString() {
// return "Person{" +
// "name='" + name + '\'' +
// ", age=" + age +
// '}';
// }
}
public class Test {
public static void main(String[] args) {
Person p1=new Person("张三",18);
Person p2=new Person("李四",58);
System.out.println(p1);
System.out.println(p2);
System.out.println(p1.equals(p2)); //false
p1=p2;
System.out.println(p1.equals(p2)); //true
}
}
3.重写equals方法
如果没有覆盖重写equals方法,那么Object类中默认进行==
运算符的对象地址比较,只要不是同一个对象,结果必然为false。
如果希望进行对象的内容比较,即所有或指定的部分成员变量相同就判定两个对象相同,则可以覆盖重写equals方法。
Object类的equals方法,默认比较的是两个对象的地址值,没有意义
所以我们要重写equals方法,比较两个对象的属性(name,age)
问题:
隐含着一个多态
多态的弊端:无法使用子类特有的内容(属性和方法)
Object obj = p2 = new Person(“古力娜扎”,19);
解决:可以使用向下转型(强转)把obj类型转换为Person
例如:
import java.util.ArrayList;
class Person{
public String name;
public int age;
public Person() {
}
public Person(String name, int age) {
this.name = name;
this.age = age;
}
@Override
public boolean equals(Object obj) {
//增加一个判断,传递的参数obj如果是this(如p1.equals(p1))本身,直接返回true,提高程序的效率
if (obj==this){
return true;
}
//增加一个判断,传递的参数obj如果是null,直接返回false,提高程序的效率
if(obj==null){
return false;
}
//增加一个判断,防止类型转换一次ClassCastException
if (obj instanceof Person){
//使用向下转型,把obj转换为Person类型
Person p=(Person)obj;
//String是属于对象所以用equals(String的equal值比较内容),int是基础类型所以用==
/*
int也可以用equals比较,只不过要转为其包装类
Integer a=12;
Integer b=12;
System.out.println(a.equals(b));//true
*/
boolean b=this.name.equals(p.name)&&this.age==p.age;
return b;
}
//不是Person类型直接返回false
return false;
}
}
public class Test {
public static void main(String[] args) {
Person p1=new Person("张三",18);
Person p2=new Person("张三",18);
//ArrayList<String> list=new ArrayList<>();
boolean b = p1.equals(p1);
System.out.println(b);
}
}
上面代码可由idea生成
@Override
public boolean equals(Object o) {
if (this == o) return true;
//getClass() != o.getClass() 使用反射技术,判断o是否是Person类型 等效于 obj instanceof Person
if (o == null || getClass() != o.getClass()) return false;
Person person = (Person) o;
return age == person.age &&
Objects.equals(name, person.name);
}
@Override
public int hashCode() {
return Objects.hash(name, age);
}
上面的**Objects.equals()**方法可以对两个对象进行比较,防止空指针异常
null是不能调用方法的,会抛出空指针异常(对象调null就可以)
public class Test {
public static void main(String[] args) {
String s1=null;
String s2="abc";
//boolean b = s1.equals(s2); //报NullPointerException异常
boolean b = Objects.equals(s1, s2);
System.out.println(b); //false不会报错
}
}
4.date(util包下的)
java.text.DateFormat:是日期/时间格式化子类的抽象类
作用:
格式化(也就是日期 -> 文本)、解析(文本-> 日期)
成员方法:
1.String format(Date date) 按照指定的模式,把Date日期,格式化为符合模式的字符串(把Fri Oct 30 17:17:20 CST 2020转为2020-10-30 17-17-20)
2.Date parse(String source) 把符合模式的字符串,解析为Date日期(把2020年10月30日 17时19分12秒变为Fri Oct 30 17:19:12 CST 2020)
DateFormat类是一个抽象类,无法直接创建对象使用,可以使用DateFormat类的子类
java.text.SimpleDateFormat extends DateFormat
构造方法:
SimpleDateFormat(String pattern)
用给定的模式和默认语言环境的日期格式符号构造 SimpleDateFormat。
参数:
String pattern:传递指定的模式
模式:区分大小写的
y 年
M 月
d 日
H 时
m 分
s 秒
写对应的模式,会把模式替换为对应的日期和时间
“yyyy-MM-dd HH:mm:ss”
注意:
模式中的字母不能更改,连接模式的符号可以改变(可把-换成汉字或者其他符号)
“yyyy年MM月dd日 HH时mm分ss秒”
import javafx.scene.SceneAntialiasing;
import java.text.ParseException;
import java.text.SimpleDateFormat;
import java.util.Date;
import java.util.Scanner;
public class Date1 {
public static void main(String[] args) throws ParseException {
//使用parse要抛出异常而已
demo6();
}
private static void demo6() throws ParseException {
/*
练习:
请使用日期时间相关的API,计算出一个人已经出生了多少天。
分析:
1.使用Scanner类中的方法next,获取出生日期
2.使用DateFormat类中的方法parse,把字符串的出生日期,解析为Date格式的出生日期
3.把Date格式的出生日期转换为毫秒值
4.获取当前的日期,转换为毫秒值
5.使用当前日期的毫秒值-出生日期的毫秒值
6.把毫秒差值转换为天(s/1000/60/60/24)
*/
//1.使用Scanner类中的方法next,获取出生日期
Scanner scanner = new Scanner(System.in);
System.out.println("请输入您的出生日期,格式:yyyy-MM-dd:");//一定要用这格式输入哦,因为用到的parse
String birthdayDateString = scanner.next();
//2.使用DateFormat类中的方法parse,把字符串的出生日期,解析为Date格式的出生日期
SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd");
Date birthdayDate = sdf.parse(birthdayDateString);
//3.把Date格式的出生日期转换为毫秒值
long birthdayDateTime = birthdayDate.getTime();
//4.获取当前的日期,转换为毫秒值
long todayTime = new Date().getTime();
//5.使用当前日期的毫秒值-出生日期的毫秒值
long time=todayTime-birthdayDateTime;
//6.把毫秒差值转换为天(s/1000/60/60/24)
System.out.println("活了:"+(time/1000/60/60/24)+"天");
}
private static void demo5() throws ParseException {
/*
使用DateFormat类中的方法parse,把文本解析为日期
使用步骤:
1.创建SimpleDateFormat对象,构造方法中传递指定的模式
2.调用SimpleDateFormat对象中的方法parse,把符合构造方法中模式的字符串,解析为Date日期
注意:
public Date parse(String source) throws ParseException
parse方法声明了一个异常叫ParseException
如果字符串和构造方法的模式不一样,那么程序就会抛出此异常
调用一个抛出了异常的方法,就必须的处理这个异常,要么throws继续抛出这个异常,要么try catch自己处理
*/
//1.创建SimpleDateFormat对象,构造方法中传递指定的模式
SimpleDateFormat sdf = new SimpleDateFormat("yyyy年MM月dd日 HH时mm分ss秒");
//2.调用SimpleDateFormat对象中的方法parse,把符合构造方法中模式的字符串,解析为Date日期
Date date = sdf.parse("2020年10月30日 17时19分12秒");//这里传入的字符串要跟上面sdf后定义的模式要一致
System.out.println(date);//Fri Oct 30 17:19:12 CST 2020
}
private static void demo4() {
/*
使用DateFormat类中的方法format,把日期格式化为文本
使用步骤:
1.创建SimpleDateFormat对象,构造方法中传递指定的模式
2.调用SimpleDateFormat对象中的方法format,按照构造方法中指定的模式,把Date日期格式化为符合模式的字符串(文本)
*/
//1.创建SimpleDateFormat对象,构造方法中传递指定的模式
SimpleDateFormat sdf = new SimpleDateFormat("yyyy年MM月dd日HH时mm分ss秒");//yy MM...不能变的,连接他们的字符可变
//2.调用SimpleDateFormat对象中的方法format,按照构造方法中指定的模式,把Date日期格式化为符合模式的字符串(文本)
Date date = new Date();
String s = sdf.format(date);
System.out.println(date); //Fri Oct 30 17:17:20 CST 2020
System.out.println(s); //2020年10月30日17时19分12秒
}
private static void demo3() {
/*
long getTime() 把日期转换为毫秒值(相当于System.currentTimeMillis()方法)
返回自 1970 年 1 月 1 日 00:00:00 GMT 以来此 Date 对象表示的毫秒数。
*/
Date date = new Date();
long time = date.getTime();
System.out.println(time);
}
private static void demo2() {
Date date=new Date(0L);
System.out.println(date); //Thu Jan 01 08:00:00 CST 1970
}
private static void demo1() {
Date date=new Date();
System.out.println(date); //Fri Oct 30 16:30:53 CST 2020
}
}