2021Java进阶篇(一)Object类以及常用API

2021Java进阶篇(一)Object类以及常用API

今天所写的是JavaSE进阶篇的第一篇,后期会给大家陆续更出来,希望多多关注转发


文章目录

  • 2021Java进阶篇(一)Object类以及常用API
  • 前言
  • 一、Object类
    • 1.1 概述
    • 1.2 toString方法
    • 1.3 equals 方法
    • 1.4 Objects 类
  • 二、时间日期类
    • 2.1 Date类
    • 2.2 DateFormat类
    • 2.3 练习
    • 2.4 Calendar类
  • 三、System类
    • 概述
    • **练习**
  • 四、StringBuilder类
    • 4.1 字符串拼接问题
  • 五、包装类
    • 5.1 装箱
    • 5.2 拆箱
    • 5.3 自动装箱与自动拆箱
    • 5.4 基本类型与字符串之间的转换
  • 总结


前言

话不多说直接上干货


一、Object类

1.1 概述

Object类是所有类的祖宗类,所有的类都继承了Object类。此类中的所有方法,子类都可以使用。在对象实例化的时候最终找到的就是Object类。一个类如果没有特别指定父类的话,那么就会默认继承Object类

下面的两个方法的效果都是一样的

public class Student() extends Object{
}

public class Student(){
}

Object类中一共有11个方法,如下所示

protected  Object clone() : 创建并返回此对象的一个副本。 
boolean equals(Object obj) : 指示其他某个对象是否与此对象“相等”。 
protected  void finalize() : 当垃圾回收器确定不存在对该对象的更多引用时,由对象的垃圾回收器调用此方法。 
Class getClass() :返回此 Object 的运行时类。 
int hashCode() :  返回该对象的哈希码值。 
void notify() :唤醒在此对象监视器上等待的单个线程。 
void notifyAll() :唤醒在此对象监视器上等待的所有线程。 
String toString() :返回该对象的字符串表示。 
void wait() :在其他线程调用此对象的 notify() 方法或 notifyAll() 方法前,导致当前线程等待。 
void wait(long timeout) : 在其他线程调用此对象的 notify() 方法或 notifyAll() 方法,或者超过指定的时间量前,导致当前线程等待。 
void wait(long timeout, int nanos) :在其他线程调用此对象的 notify() 方法或 notifyAll() 方法,或者其他某个线程中断当前线程,或者已超过某个实际时间量前,导致当前线程等待。 

而我们几天主要是学习其中的两个方法

public String toString():返回该对象的字符串表示。
public boolean equals(Object obj):指示其他某个对象是否与此对象“相等”。

1.2 toString方法

方法摘要
public String toString():返回该对象的字符串表示。
toString方法返回当前对象的字符串表示形式,该字符串的内容为全限定类名+@+内存地址值

由于 toString 方法返回的结果是内存地址值,而在我们日常的开发中,经常需要按照对象的属性得到相应的字符串形式,所以我们也需要重写该方法
在JDK中有的类已经重写过了toString,而有的类则并没有

// 该类并没有重写toString,所以直接打印该对象得到的结果是全限定类名+@+内存地址值
Random random = new Random();
System.out.println(random); // java.util.Random@129a8472

// 该类则已经默认重写了toString,所以我们直接打印得到的是其内容
ArrayList<String> arrayList = new ArrayList<>();
arrayList.add("张三");
arrayList.add("王五");
arrayList.add("赵六");
System.out.println(arrayList);// [张三, 王五, 赵六]

如果我们自定义的类不想使用toString方法的默认行为的时候,也可以自己来重写该方法

// 自定义Person类
public class Person(){
	private String name;
	private Integer age;
	@Override
	public String toString(){
		return "Person[" + "name =" + name + "age =" + age + "]";
	}
}
当我们使用的是IDEA的话,则可以选择自动生成的方法【 alt + insert 】,大大节省我们的时间

1.3 equals 方法

方法摘要
public boolean equals(Object obj):指示其他某个对象是否与此对象“相等”。

调用成员方法equals并指定参数为另一个对象,则可以判断这两个对象是否是相同的,这里的相同默认自定义两种方式。

默认地址比较

如果没有重写equals方法,那么Object类中默认进行==运算符的对象地址比较,只要不是同一个对象,结果必然是false

// 当前未重写 equals 方法
public class Person(){
	private String name;
	private Integer age;
	public String getName() {
        return name;
    }

    public void setName(String name) {
        this.name = name;
    }

    public Integer getAge() {
        return age;
    }

    public void setAge(Integer age) {
        this.age = age;
    }
}

public class TestDemo(){
	public static void main(String[] args){
		Person person = new Person();
		Person person2 = new Person();
		System.out.println(person.equals(person2));	// 结果为false
	}
}
因为当前并未重写equals方法,所以进行的是地址值的比较,然后我们是 new 了两个 Person 对象,在内存中有两个不同地址值的Person对象,当我们使用equals进行比较的时候,结果必然为false

对象内容比较

如果希望进行对象的内容比较,即所有或指定的部分成员变量相同就判断两个对象相同,则可以重写equals方法

// 当前重写了equals方法
public class Person(){
	private String name;
	private Integer age;
	
	  @Override
    public boolean equals(Object o) {
    	// 如果对象地址一样,则认为相同
        if (this == o) return true;
        // 如果参数为空,或者类型信息不一样,则认为不同
        if (o == null || getClass() != o.getClass()) return false;
        // 转换为当前类型
        Person person = (Person) o;
        return Objects.equals(name, person.name) &&
                Objects.equals(age, person.age);
    }
}

public class TestDemo(){
	public static void main(String[] args){
		Person person = new Person();
		Person person2 = new Person();
		System.out.println(person.equals(person2));	// 结果为true
	}
}
当我们重写完equals 方法之后,返回的结果则变成了true

1.4 Objects 类

概述
Objects类是一个工具类,里面提供了一些方法来操作对象,它是由一些静态的实用方法组成,这些方式是空指针安全(null-save)的或容忍空指针(null-tolerant)的,用于计算对象的hashcode、返回对象的字符串表示形式、比较两个对象。

在比较两个对象的时候,Object的equals方法容易抛出空指针异常,而Objects类中的equals方法则优化了这个问题,增加了健壮性判断。

public static boolean equals(Object a, Object b):判断两个对象是否相等。

// 具体源码如下
public static boolean equals(Object a, Obj ect b) {
	return (a == b) || (a != null && a.equals(b));
}
// 使用示范
String s1 = null;
String s2 = "aaa";
System.out.println(Objects.equals(s1,s2));// 结果为false 并不会出现空指针异常

二、时间日期类

2.1 Date类

概述
java.util.Date:表示日期和时间的类。类 Date 表示特定的瞬间,精确到毫秒(千分之一秒)。毫秒值的作用:可以对时间和日期进行计算。
时间原点(0毫秒):1970年1月1日 00:00 (英国格林威治)

	tips:
		中国属于东八区,会把时间增加8个小时
		1970年1月1日 08:00

把毫秒转换为日期:

	1天 = 24 * 60 * 60 = 86400 秒 = 86400 * 1000 = 86400000毫秒

构造方法

		//	Date() 根据当前系统时间创建日期对象
        Date date = new Date();
        System.out.println(date);	// Wed Apr 14 18:52:55 CST 2021
        //	Date(long time) 根据传入的毫秒值时间创建日期对象
        Date date2 = new Date(1576031400L);
        System.out.println(date2);	// Mon Jan 19 13:47:11 CST 1970

常用方法
Date类中的大多数方法已经过时,常用的方法有
public long getTime() 把日期对象转换成对应的时间毫秒值
public String toLocalString(Date date) 根据本地格式转换日期对象【已过时】(在此只是为了演示)

 		//	long getTime() 获取当前日期对象的毫秒值时间
        Date date = new Date();
        long l1 = date.getTime();
        System.out.println(l1); // 1618397846868
        //	String toLocaleString() 根据本地格式转换日期对象【该方法已过期】
        String str = l1.toLocalString();
        System.out.println(str);	//	2021年4月14日 下午6:58:55

2.2 DateFormat类

概述
java.text.DateFormat 是日期/时间格式化子类的抽象类,我们通过这个类可以帮我们完成日期和文本之间的转化,也就是在Date对象和Strign对象之间进行来回转换

格式化:按照指定的格式,把Date对象转换为Strign对象
解析:按照指定的格式,把String对象转换为Date对象

构造方法
因为DateFormat类是一个抽象类,不能直接进行使用,所以需要子类来继承它

常用子类
java.text.SimpleDateFormat 这个类需要一个格式 (模式) 来指定格式化或解析的标准。构造方法如下:
public SimpleDateFormat(String pattern):用给定的模式和默认语言环境的日期格式符号构造SimpleDateFormat

参数 pattern 是一个字符串,表示时间日期的自定义格式

格式规则
2021Java进阶篇(一)Object类以及常用API_第1张图片

tips:
	更详细的格式规则可以参考SimpleDateFormat类的API文档

创建SimpleDateFormat对象的代码如下

public class DemoSimpleDateFormat{
	public static void main(String[] args){
	// 以下两种写法都可以
	// 多态写法
		DateFormat dateFormat = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");
	// 正常写法
		SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");
	}
}

常用方法
DateFormat类的常用方法有

public String format(Date date):将Date对象格式化为字符串

public class TestDemo{
	public static void main(String[] args){
		Date date = new Date();
		DateFormat dateFormat = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");
		String str = dateFormat.format(date);
		System.out.println(str);	//	2021-04-14 19:20:39
		
		//	格式中使用中文这样的方式同样可以
		SimpleDateFormat sdf = new SimpleDateFormat("yyyy年MM月dd日 HH时mm分ss秒");
        String format = sdf.format(date);
        System.out.println(format);	// 2021年04月14日 19时19分27秒
	}
}

public Date parse(String source):将字符串解析为Date对象

public class TestDemo throws ParseException{
	public static void main(String[] args){
		//	创建SimpleDateFormat对象,构造方法中传递指定的模式
        SimpleDateFormat sdf = new SimpleDateFormat("yyyy年MM月dd日 HH时mm分ss秒");
        // 该方法有异常 需要进行抛出
        Date date = sdf.parse("2021年04月14日 17时01分10秒");
        System.out.println(date);	// Wed Apr 14 17:01:10 CST 2021
	}
}

2.3 练习

请使用日期时间相关的API,计算出一个人已经出生了多少天

public static void function() throws Exception {
	System.out.println("请输入出生日期,格式为: yyyy-MM-dd");
	// 获取出生日期,从键盘录入
	Scanner sc = new Scanner(System.in);
	String birthDay = sc.next();
	// 将字符串日期转化为Date对象
	// 创建SimpleDateFormat对象,使用 parse() 方法
	SimpleDateFormat sdf = new SimpleDateFormat("
	yyyy-MM-dd");
	// 把字符串日期转换为Date类型
	Date birthdayTime = sdf.parse(birthDay);
	// 获取当前的日期
	Date date = new Date();
	// 将当前日期转化为毫秒值
	Long now = date.getTime();
	// 把 birthdayTime 转化为毫秒值
	Long birth = birthdayTime.getTime();
	// 使用 当前日期 减去 birth 
	Long actually = now - birth;
	// 增加健壮性判断
	if(actually < 0){
		System.out.println("还没出生呢!!!");
	}else{
		System.out.println("您已经生活了:"+actually/1000/60/60/24+"天");
	}
}

2.4 Calendar类

概述

java.util.Calendar是日历类,在Date后出现的,替换掉了很多Date的方法。该类将所有可能用到的时间信息封装为静态成员变量方便获取,日历类就是为了方便获取各个时间属性的。

获取方法

Calendar为抽象类【里面提供了很多操作日历字段的方法(YEAR MONTH DAT_OF HOUR)】,由于语言敏感性,所以Calendar类在创建的时候并非直接创建,而是通过静态方法创建返回子类对象
Calendar静态方法
public static Calendar getInstance():使用默认时区和语言环境获得一个日历

public class TestDemo(){
	public static void main(String[] args){
		Calendar cal = Calendar.getInstance();
		System.out.println(cal);
	}
}

常用方法

Calendar类的成员方法

public int get(int field): 返回给定日历字段的值
public void ser(int field,int value): 将给定的日历字段设置为定值
public abstract void add(int field, int amount): 根据日历的规则,为给定的日历字段添加或减去指定的时间量
public Date getTime():返回一个表示Calendar时间值(从历元到现在的毫秒偏移值)的Date对象

成员方法的参数

int field:日历类的字段,可以使用Calendar类的静态成员变量获取
public static final int YEAR = 1; 年
public static final int MONTH = 2; 月
public static final int DATE = 5; 月中的某一天
public static final int DAY_OF_MONTH = 5; 月中的某一天
public static final int HOUR = 10; 时
public static final int MINUTE = 12; 分
public static final int SECOND = 13; 秒

Calendar类中提供很多成员常量,代表给定的日历字段:
2021Java进阶篇(一)Object类以及常用API_第2张图片

方法演示

public int get(int field) :返回给定日历字段的值

Calendar c = Calendar.getInstance();
int year = c.get(Calendar.YEAR);
System.out.println(year);	// 2021

int month = c.get(Calendar.MONTH);
//	西方的月份0-11,东方的月份:1-12
System.out.println(month + 1);	// 4

int date = c.get(Calendar.DATE);
System.out.println(date);// 14

public void ser(int field,int value): 将给定的日历字段设置为定值
参数:
int field 传递的指定日历字段(YEAR,MONTH…)
int value 日历字段代表具体的值

Calendar c = Calendar.getInstance();
//	设置年为9999
c.set(Calendar.YEAR,9999);
//	设置月为9
c.set(Calendar.MONTH,9);
//	设置日为9
c.set(Calendar.DATE,9);
//	同时设置年月日,使用set的重载方法
c.set(8888,8,8);
int year = c.get(Calendar.YEAR);
System.out.println(year);	//	8888
int month = c.get(Calendar.MONTH);
//西方的月份0-11,东方的月份:1-12
System.out.println(month);	// 8
int date = c.get(Calendar.DATE);
System.out.println(date);	// 8

public abstract void add(int field, int amount): 根据日历的规则,为给定的日历字段添加或减去指定的时间量。把指定的字段增加/减少指定的值
参数
int field 传递指定的日历字段(YEAR,MONTH…)
int amount 增加/减少的值
正数:增加 负数:减少

Calendar c = Calendar.getInstance();
//	把年增加2年
c.add(Calendar.YEAR,2);
int year = c.get(Calendar.YEAR);
System.out.println(year);	// 2023
//	把月份减少2年
c.add(Calendar.MONTH,-2);
int year2 = c.get(Calendar.YEAR);
System.out.println(year);	// 2019
int month = c.get(Calendar.MONTH);
//西方的月份0-11,东方的月份:1-12
System.out.println(month);	// 1
int date = c.get(Calendar.DATE);
System.out.println(date);	// 14

public Date getTime():返回一个表示Calendar时间值(从历元到现在的毫秒偏移值)的Date对象

Calendar c = Calendar.getInstance();
Date date = c.getTime();
System.out.println(date);

三、System类

概述

java.lang.System类中提供了大量的静态方法,可以获取与系统相关的信息或系统级操作,在System类的API文档中,常用的方法有:

  • public static long currentTimeMillis():返回以毫秒为单位的当前时间。
public class SystemDemo {
    public static void main(String[] args) {
       	//获取当前时间毫秒值
        System.out.println(System.currentTimeMillis()); // 1618401766987
    }
}

练习

//        程序执行前,获取一次毫秒值
        long s = System.currentTimeMillis();
//      执行for循环
        for (int i = 0; i < 9999; i++) {
            System.out.println(i);
        }
//        程序执行后,再次获取毫秒值
        long s1 = System.currentTimeMillis();
//        用执行后的毫秒值减去执行前的毫秒值
        long s2 = s1 - s;
        System.out.println("程序共耗时" + s2 + "毫秒");
  • public static void arraycopy(Object src, int srcPos, Object dest, int destPos, int length):将数组中指定的数据拷贝到另一个数组中。
    数组的拷贝动作是系统级的,性能很高。System.arraycopy方法具有5个参数,含义分别为
    2021Java进阶篇(一)Object类以及常用API_第3张图片
    练习
    将src数组中前3个元素,复制到dest数组的前3个位置上复制元素前:src数组元素[1,2,3,4,5],dest数组元素[6,7,8,9,10]复制元素后:src数组元素[1,2,3,4,5],dest数组元素[1,2,3,9,10]
public class Demo11SystemArrayCopy {
    public static void main(String[] args) {
        int[] src = new int[]{1,2,3,4,5};
        int[] dest = new int[]{6,7,8,9,10};
        System.arraycopy( src, 0, dest, 0, 3);
        /*代码运行后:两个数组中的元素发生了变化
         src数组元素[1,2,3,4,5]
         dest数组元素[1,2,3,9,10]
        */
    }
}

四、StringBuilder类

4.1 字符串拼接问题

String类 字符串时常量,它们的值在创建之后不能更改。字符串的底层时一个被final修饰的数组,不能更改,是一个常量 : private final byte[] value
由于String类的对象内容不可改变,所以每当进行字符串拼接的时候,总是会在内存中创建一个新的对象

public class StringDemo {
    public static void main(String[] args) {
        String s = "Hello";
        s += "World";
        System.out.println(s);
    }
}

StringBuilder类: 字符串缓冲区,可以提高字符串的操作效率(看成一个长度可以变化的字符串),底层也是一个数组,但是没有被final修饰,可以改变长度byte[] value = new byte[16]

StringBuilder在内存中始终时一个数组,占用空间少,效率高,如果超出了StringBuilder的容量,会自动的扩容

构造方法

  • public StringBuilder():构造一个空的StringBuilder容器。
  • public StringBuilder(String str):构造一个StringBuilder容器,并将字符串添加进去。
public class StringBuilderDemo {
    public static void main(String[] args) {
        StringBuilder sb1 = new StringBuilder();
        System.out.println(sb1); // (空白)
        // 使用带参构造
        StringBuilder sb2 = new StringBuilder("hello");
        System.out.println(sb2); // hello
    }
}

常用方法

  • public StringBuilder append(…)`:添加任意类型数据的字符串形式,并返回当前对象自身
public class Demo02StringBuilder {
    public static void main(String[] args) {
		StringBuilder builder = new StringBuilder();
		builder.append("abc");
        builder.append(1);
        builder.append('z');
        builder.append("zhong");
        builder.append("abc");
        System.out.println(builder);// abc1zzhongabc
	}
}

// StringBuilder 已经重写了Object当中的toString方法
  • public String toString():将当前StringBuilder对象转换为String对象
public class Demo16StringBuilder {
    public static void main(String[] args) {
    	// 在我们开发中,会遇到调用一个方法后,返回一个对象的情况。然后使用返回的对象继续调用方法。
        // 这种时候,我们就可以把代码现在一起,如append方法一样,代码如下
        // 链式创建
        StringBuilder sb = new StringBuilder("Hello").append("World").append("Java");
        // 调用方法
        String str = sb.toString();
        System.out.println(str); // HelloWorldJava
    }
}

五、包装类

概述
基本数据类型的数据,使用起来非常的方便,但是没有对应的方法来操作这些数据,所以我们可以使用一个类,把基本类型的数据包装起来,这个类叫包装类,在包装类中可以定义一些方法,用来操作基本类型的数据。
2021Java进阶篇(一)Object类以及常用API_第4张图片

5.1 装箱

装箱:把基本类型的数据,包装到包装类中(基本数据类的数据->包装类)

构造方法

Integer(int value) 构造一个新分配的Integer对象,他表示指定的int值
Integer(String s) 构造一个新分配的Integer对象,他表示String参数所指示的int值

传递的字符串,必须是基本类型的字符串,否则会抛出异常【"100"正确】,【"a"抛出异常】

静态方法
static Integer valueOf(int i) 返回一个表示指定的int值的Integer实例
static Integer valueOf(String s) 返回保存指定的String的值的Integer对象

//  装箱:把基本类型的数据,包装到包装类中(基本数据类的数据->包装类)、
Integer in1 = new Integer(1);//方法上有横线,表示方法过时了
System.out.println(in1);//重写了toString方法
Integer in2 = new Integer("1");
System.out.println(in2);
// 静态方法
Integer in3 = Integer.valueOf(2);
System.out.println(in3);
// Integer in4 = Integer.valueOf("a");//NumberFormatException 数字格式化异常 错误写法
Integer in4 = Integer.valueOf("2");
System.out.println(in4);

5.2 拆箱

拆箱:在包装类中取出基本类型的数据(包装类->基本数据类型)
成员方法
int intValue() 以int类型返回该Integer的值

// 在包装类中取出基本类型的数据(包装类->基本数据类型)
int i = in1.intValue();
System.out.println(i);

5.3 自动装箱与自动拆箱

由于我们经常要做基本类型与包装类之间的转换,从Java 5(JDK 1.5)开始,基本类型与包装类的装箱、拆箱动作可以自动完成

自动装箱:直接把int类型的数据赋值给包装类

Integer in = 1; // 就相当于 Integer in = new Integer(1);

自动拆箱:in是包装类,无法直接参加运算,但是可以自动转换为基本类型的数据,再参与计算

in += 2 就相当于in.intValue() + 3 = 3
in = in + 2 就相当于 in = new Integer(2) 自动装箱

5.4 基本类型与字符串之间的转换

基本类型转换为String【共三种方式】

1.基本类型数据的值+"" 最简单的方式(工作中常用)
2.使用包装类的静态方法
static String toString(int i) 返回一个表示指定整数的 String 对象
3.使用String类中的静态方法
static String valueOf(int i) 返回int 参数的字符串表示形式

String s1 = 100 + "";
System.out.println(s1 + 200);//100200

String s2 = Integer.toString(100);
System.out.println(s2 + 200);//100200

String s3 = String.valueOf(100);
System.out.println(s3 + 200);//100200

String转换成对应的基本类型
除了Character类之外,其他所有包装类都具有parseXxx静态方法可以将字符串参数转换为对应的基本类型

  • public static byte parseByte(String s):将字符串参数转换为对应的byte基本类型。
  • public static short parseShort(String s):将字符串参数转换为对应的short基本类型。
  • public static int parseInt(String s):将字符串参数转换为对应的int基本类型。
  • public static long parseLong(String s):将字符串参数转换为对应的long基本类型。
  • public static float parseFloat(String s):将字符串参数转换为对应的float基本类型。
  • public static double parseDouble(String s):将字符串参数转换为对应的double基本类型。
  • public static boolean parseBoolean(String s):将字符串参数转换为对应的boolean基本类型。
// 此处只演示 Integer 转换成 int
public class TestDemo(){
	public static void main(String[] args){
		int i = Integer.parseInt("100");
        System.out.println(i + 200);//300

		// 如果字符串参数的内容无法正确转换为对应的基本类型,则会抛出 java.lang.NumberFormatException 异常。
		int i2 = Integer.parseInt("a");
		System.out.println(i2);
	}
}

总结

今天的分享到这里就结束了,如果觉得写的还不错的话可以多多关注点赞转发哦,本系列会持续更新!!!

你可能感兴趣的:(笔记,个人学习,java,后端)