JavaSE进阶:常用类(一)

本文详细介绍了Java中的内部类,包括成员内部类、静态内部类、局部内部类和匿名内部类的概念、特点和使用示例。此外,还深入讲解了Object类的关键方法如getClass()、hashCode()、toString(),以及equals()方法和双等于运算符的区别。同时,探讨了包装类的作用,特别是Integer类的缓冲区特性,以及装箱、拆箱的概念。
摘要由CSDN通过智能技术生成

目录

1.内部类

1.内部类分类、内部类特点

1.分类

2.内部类特点

2.成员内部类

3.静态内部类

4.局部内部类

5.匿名内部类

2.Object类

1.Object类概述

2.getClass()方法

3.hashCode方法

4.toString方法

1.双等于(==)与equals的区别

5.equals()方法

6.finalize()方法

7.Objects类

1.equals()方法

2.isNull方法

8.实例

3.包装类

1.类型转换与装箱拆箱

1.装箱、拆箱

2.类型转换

2.Integer(整数)缓冲区


1.内部类

1.内部类分类、内部类特点

1.分类

成员内部类、静态内部类、局部内部类、匿名内部类
概念:在一个类的内部再定义一个的类。内部类本身就是类的 一个属性,与其他属性定义方式一致

2.内部类特点

  • 编译之后可生成独立的字节码文件(class文件)
  • 内部类可以直接访问外部类的私有成员和普通成员
  • 内部类不为同一包的其他类所见,具有很好的封装性
  • 内部类有效实现了“多重继承”,优化 java 单继承的缺陷。
  • 可以为外部类提供必要的内部功能组件
例:
package java_se.java_jinjie.neibulei;

public class Demo1 {//外部类
    private String name;
    class Header{//内部类 内部类也会生成class文件
        public void show(){
            System.out.println(name);
        }
    }
}


2.成员内部类

在类的内部定义,与实例变量、实例方法同级别的类。
成员内部类可以访问外部类所有的变量和方法,包括静态和非静态,私有和公有,创建内部类对象时,必须依赖外部类对象。
Outer outer = new Outer() ;
Outer.Inner in = outer.new Inner() ;
当外部类、内部类存在重名属性时,会优先访问内部类属性
成员内部不能定义静态成员,但是可以定义静态常量

例:
package java_se.java_jinjie.neibulei.demo;
//外部类
public class Outer {
    //实例对象(变量)
    private String name="张三";
    private int age=20;
    //内部类
    class Inner{
        private String address="北京";
        private String phone="110";
        private String name="李四";
        //成员内部类不能定义静态成员,但是可以定义静态常量
//        private static String country="中国";//static会报错
        private static final String country2="中国";//静态常量却不会报错
        //方法
        public void show(){
            //打印外部类的属性  为了区分内部类和外部类外部类可以提前加上Outer.this.
            //外部类与内部类存在重名属性,会打印内部类,如果要打印外部类则前面加Outer.this.
            System.out.println(Outer.this.name);//张三
            System.out.println(age);
            //打印内部类属性   内部类平时可以提前加上this.来更好分清内部类外部类
            System.out.println(address);
            System.out.println(phone);
            System.out.println(name);//李四
            //静态常量可以正常运行
            System.out.println(country2);//中国
        }
    }
}
/*
package java_se.java_jinjie.neibulei.demo;

public class TestOuter {
    public static void main(String[] args) {
//        //1.创建外部类对象
//        Outer outer = new Outer();
//        //2.创建内部类对象
//        Outer.Inner inner = outer.new Inner();
        //一步到位        Outer带()表示创建对象
        Outer.Inner inner=new Outer().new Inner();
        inner.show();//创建内部类对象后,直接使用内部类方法
    }
}
 */

3.静态内部类

定义在类内部的静态类,就是静态内部类。

不依赖外部类对象,可直接创建或通过类名访问,可声明静态成员。
只能直接访问外部类的静态成员(实例成员需实例化外部类对象),

outer. lmner inner = new outer. Imner() ;
Outer. laner. show();
只有内部类可以用static修饰,普通类不可以使用static

例:
package java_se.java_jinjie.neibulei.demo01;
//外部类
public class Outer {
    private String name="xxx";
    private int age=18;
    //静态内部类,和外部类相同
    static class Inner{
        private String address="上海";
        private String phone="111";
        //静态成员
        private static int count=1000;
        public void show(){
            //调用外部类的属性
            //1.先创建外部类对象
            Outer outer = new Outer();
            //2.调用外部类对象的属性
            System.out.println(outer.name);
            System.out.println(outer.age);
            //调用静态内部类的属性和方法
            System.out.println(address);
            System.out.println(phone);
            //调用静态内部类的静态属性
            System.out.println(Inner.count);
        }
    }
}
/*
package java_se.java_jinjie.neibulei.demo01;

public class TestOuter {
    public static void main(String[] args) {
        //直接创建内部类对象         Outer没有带()表示包含关系
        Outer.Inner inner= new Outer.Inner();
        //调用方法
        inner.show();
    }
}
 */

4.局部内部类

放在方法、代码块、构造器等执行体中的类就是局部内部类。

如果定义在外部类方法中,作用范围和创建对象范围仅限于当前方法,不能使用权限修饰符,静态不能用。
局部内部类访问外部类当前方法中的局部变量时,因无法保障变量的生命周期与自身相同,变量必须修饰为final。
使用范围有限,只能在当前方法使用

例:
package java_se.java_jinjie.neibulei.demo02;
//外部类
public class Outer {
    //实例变量
    private String name="刘德华";
    private int age = 35;
    public void show(){
        //定义局部变量    方法执行完后,局部变量消失
        final String address="深圳";
        //局部内部类:注意不能加任何访问修饰符
        class Inner{//使用后类不会消失
            //局部内部类的属性
            private String phone="110";
            private String email="110@qq.com";
            public void show2(){
                //访问外部类属性
                System.out.println(Outer.this.name);
                System.out.println(Outer.this.age);
                //访问内部类属性
                System.out.println(this.phone);
                System.out.println(this.email);
                //访问局部变量 jk1.7要求:变量必须是常量final,jdk1.8自动添加final(默认是)
                System.out.println(address);//加上final访问的是实际常量
            }
        }
        //创建局部内部类对象 使用后Inner并不会立即消失
        Inner inner = new Inner();
        inner.show2();
    }
}
/*测试
package java_se.java_jinjie.neibulei.demo02;

public class TexstOuter {
    public static void main(String[] args) {
        Outer outer = new Outer();
        outer.show();
    }
}
 */

5.匿名内部类

  • 没有类名的局部内部类(一切特征都与局部内部类相同)
  • 必须继承一个抽象类或者实现一个接口。
  • 不能定义任何静态成员和静态方法
  • 定义类、实现类、创建对象的语法合并,只能创建一个该类的对象。
  • 当所在的方法的形参需要被匿名内部类使用时,必须声明为 final。 匿名内部类不能是抽象的,它
  • 必须要实现继承的类或者实现的接口的所有抽象方法。

优点:减少代码量。方便创建子类对象
缺点:可读性较差。

匿名内部类产生的对象类型(左边),相当于是当前new的那个的类型的子类类型

例:
package java_se.java_jinjie.neibulei.demo03;

public class TestUSB {
    public static void main(String[] args) {
        //创建接口类型的变量 第一种
//        USB usb = new Mouse();
//        usb.service();
//        //局部内部类 第二种
//        class Fan implements USB{
//            @Override
//            public void service() {
//                System.out.println("链接电脑成功,风扇开始工作了");
//            }
//        }
//        //使用局部内部类创建对象
//        USB usb = new Fan();
//        usb.service();
        //匿名内部类优化(相当于创建了一个局部内部类)   第三种
        USB usb = new USB(){//这里的USB可以是接口也可以是抽象类也是可以是父类,在里边重写方法就可以了
            @Override
            public void service() {
                System.out.println("链接电脑成功,风扇开始工作了");
            }
        };
        usb.service();
    }
}
/*接口
package java_se.java_jinjie.neibulei.demo03;
//接口
public interface USB {
    //服务方法
    void service();
}
链接接口
package java_se.java_jinjie.neibulei.demo03;

public class Mouse implements USB{
    @Override
    public void service() {
        System.out.println("链接电脑成功,鼠标开始工作");
    }
}
 */

2.Object类

1.Object类概述

超类、基类,所有类的直接或间接继承父类,位于继承树的最顶层。
任何类,如没有书写extends显示继承某个类,都默认直接继承0bject类,否则为间接继承
0bject类中所定义的方法,是所有对象都具备的方法。.
0bject类型可以存储任何对象。
    作为参数,可接受任何对象。
    作为返回值,可返回任何对象。

2.getClass()方法

public final Class<?> getClass() {}
返回引用中存储的实际对象类型。
应用:通常用于判断两个引用中实际存储对象类型是否一致。

3.hashCode方法

public int hashCode() {}
返回该对象的哈希码值。
哈希值根据对象的地址或字符串或数字使用hash算法计算出来的int类型的数值
一般情况下相同对象返回相同哈希码。

4.toString方法

public String toString() {}
返回该对象的字符串表示(表现形式)。
可以根据程序需求覆盖该方法,如:展示对象各个属性值。
一般情况下相同对象返回相同哈希码。

1.双等于(==)与equals的区别

对于“==”运算符

1.它的作用是判断两个对象的地址是不是相等

2.用于基本数据类型相互比较,比较二者的值是否相等。
3.用于引用数据类型相互比较,比较二者(内存)地址是否相等。
4.不能用于基本数据类型与引用型比较。

对于equals()方法

1.不能用于基本数据类型比较,只能用于引用数据类型。
1.判断两个对象是否相等,比较的是二者的引用地址是否相同。

2.对象的相等与指向他们的引用相等有什么区别

  • 对象的相等 比的是内存中存放的内容是否相等
  • 引用相等 比较的是他们指向的内存地址是否相等

5.equals()方法

public boolean equals(Object obj){}
默认实现为(this == obj), 比较两个对象地址是否相同
可进行重写,默认重写是来自String类用来比较两个对象的内容是否相同

6.finalize()方法

当对象被判定为垃圾对象时,由JVM自动调用此方法,用以标记垃圾对象,进入回收队列
垃圾对象:没有有效引用指向此对象时,为垃圾对象
垃圾回收:由gc销毁垃圾对象,释放数据存储空间
自动回收机制:JVM的内存耗尽,一次性回收所有垃圾对象
手动回收机制:使用System.gc();通知JVM执行垃圾回收

7.Objects类

1.equals()方法

public static boolean equals(Object a, Object b)

比较两个对象的底层会先进行非空判断,从而可以避免空指针异常再进行equals比较,后跟两个参数。

public static boolean equals(Object a, Object b) {
    return (a == b) || (a != null && a.equals(b));
}

2.isNull方法

public static boolean isNull(Object obj)

判断变量是否为null ,null返回true ,反之

8.实例

package java_se.java_jinjie.neibulei.demo04;

public class Test {
    public static void  main(String[] args) {
        Student s4 = new Student("aaa",20);
        Student s41 = new Student("bbb",21);
        //1.getClass方法
        //判断s4和s41是不是同一个类型
        Class class4=s4.getClass();
        Class class41=s41.getClass();
        if (class4==class41){
            System.out.println("s4和s41是同一类型");//√
        }else {
            System.out.println("s4和s41不是同一类型");
        }
        System.out.println("===========");
        //2.hashCode方法
        //返回该对象的哈希值
        System.out.println(s41.hashCode());
        System.out.println(s4.hashCode());
        Student s42=s41;
        System.out.println(s42.hashCode());
        System.out.println("===========");
        //3.toString方法
        //返回该对象的字符串表示
        System.out.println(s4.toString());
        System.out.println(s41.toString());
        System.out.println("===========");
        //4.equals方法
        //在Object中比较两个对象的地址或内容是否相同,但在String类中只比较内容
        System.out.println(s4.equals(s41));             //false
        Student s43 = new Student("小明", 19);
        Student s44 = new Student("小明", 19);
        System.out.println(s43.equals(s44));//两个数值一样但是equals值不一样,去Student
        System.out.println("===========");

    }
}
/*Student类
package java_se.java_jinjie.neibulei.demo04;

public class Student extends Object {
    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) {
        this.age = age;
    }
    //3.toString 返回该对象的字符串表示
    @Override
    public String toString() {
        return "Student{" +
                "name='" + name + '\'' +
                ", age=" + age +
                '}';
    }
    //4.equals方法 比较两个对象的地址或内容是否相同
    @Override
    public boolean equals(Object obj) {
        //1.判断两个对象是否是同一个引用
        if (this==obj){
            return true;
        }
        //判断obj是否为空
        if (obj==null){
            return false;
        }
        //instanceof 判断对象是否是某种类型
        if (obj instanceof Student){
            //强制类型转换
            Student s= (Student) obj;
            //比较属性
            if (this.name.equals(s.getName())&&this.age==s.getAge()){
                return true;
            }
        }
        return false;
    }
    //5.finalize方法 垃圾回收
    //二
    @Override
    protected void finalize() throws Throwable {
        System.out.println(this.name+"对象被回收了");
    }
}
测试类2
package java_se.java_jinjie.neibulei.demo04;
//5.finalize 垃圾回收
public class Test2 {
    public static void main(String[] args) {
//        //一
//        Student s1 = new Student("aaa",20);//不是垃圾没有被回收,O:回收垃圾
//        Student s2 = new Student("bbb",20);

        //二
        new Student("aaa",20);//是垃圾被回收了,O:aaa对象被回收了...回收垃圾
        new Student("bbb",20);

        //回收垃圾
        System.gc();
        System.out.println("回收垃圾");//一
    }
}
 */

3.包装类

基本数据类型所对应的引用数据类型

Object 可统一所有数据,包装类的默认值是null

基本数据类型包装类型
byteByte
shortShort
intInteger
longLong
floatFloat
doubleDouble
booleanBoolean
charCharacter

1.类型转换与装箱拆箱

8种包装类提供不同类型间的转换方式
        Number父类中提供的6个共性方法
        parseXXX( )静态方法//字符串转基本类型
        valueOf( )静态方法//装箱

注意:需保证类型兼容,否则抛出NumberFormatException异常

1.装箱、拆箱

装箱:装箱,基本类型转成引用类型的过程(从栈空间转到堆空间)
拆箱:拆箱,引用类型转换成基本类型(从堆空间转到栈空间)

    package java_se.java_jinjie.neibulei.demo05;

public class Demo {
    public static void main(String[] args) {
//        int num=1;
        //类型转换:装箱,基本类型转成引用类型的过程(从栈空间转到堆空间)
        //基本类型
        int num1=2;
        //使用Integer类型创建对象
        Integer integer1 = new Integer(num1);
        Integer integer2 = Integer.valueOf(num1);
        System.out.println("装箱");
        System.out.println(integer1);
        System.out.println(integer2);

        //类型转换:拆箱,引用类型转换成基本类型(从堆空间转到栈空间)
        Integer integer3 = new Integer(100);
        int num2 = integer3.intValue();
        System.out.println("拆箱");
        System.out.println(num2);

        //JDK1.5之后,提供自动装箱和拆箱
        int age=30;
        //自动装箱
        Integer integer=age;
        System.out.println("自动装箱");
        System.out.println(integer);
        //自动拆箱
        int age2=integer;
        System.out.println("自动拆箱");
        System.out.println(age2);
    }
}

2.类型转换

基本类型转字符串类型:String s2 = Integer.toString(n1);//16

基本类型转x进制:String s3 = Integer.toString(n1, x);//x的值为几进制(如16进制的数字16为f)


    package java_se.java_jinjie.neibulei.demo05;

public class Demo {
    public static void main(String[] args) {
        System.out.println("----基本类型和字符串之间转换----");
        //基本类型和字符串之间转换
        //1.基本类型转成字符串
        int n1=16;
        //1.1字符串使用+号
        String s1=n1+"";
        System.out.println(s1);
        //1.2使用Integer中的toString()方法
        String s2 = Integer.toString(n1);//16
        String s3 = Integer.toString(n1, 16);//f  radix为进制要求
        System.out.println(s2);
        System.out.println(s3);
        //2.字符串转成基本类型
        String str="150";//字符串转基本类型不能出现非基本类型的内容否则报错
        //如果字符串为150j则会报(NumberFormatException数字格式化异常)的错误
        //使用Integer.parseXXX()
        int n2 = Integer.parseInt(str);
        System.out.println(n2);

        //boolean字符串形式转成基本类型,"true"-->true 非"true"(如tree或false等)-->false
        String str2="true";
        boolean b1 = Boolean.parseBoolean(str2);
        System.out.println(b1);
    }
}


2.Integer(整数)缓冲区

Java预先创建了256个常用的整数包装类型对象//(-128到127)整数缓冲区,这些数都是先前已经被创建好的,调用他们的时候地址不变,而超过缓冲区的数则会重新给数字创建新的地址

在实际应用当中,对已创建的对象进行复用

package java_se.java_jinjie.neibulei.demo05;

public class Demo1 {
    public static void main(String[] args) {
        Integer integer1 = new Integer(100);
        Integer integer2 = new Integer(100);
        //==判断地址是否相同
        System.out.println(integer1 == integer2);// false

        Integer integer3 =100;// 自动装箱
        //相当于调用Integer.valueOf(100)
        //Integer integer3 = new Integer(100);
        //Integer integer3 = Integer.valueOf(100);
        Integer integer4 =100;
        System.out.println(integer3 == integer4);// true

        Integer integer5 = 200;// 自动装箱
        Integer integer6 = 200;
        System.out.println(integer5 == integer6); // false

        //因为缓存区里数组[-128,127]-128到127之间的地址已经被提前创建好位置,所地址一样,然而超过数组缓冲区的数字需要重新创建地址
    }
}

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值