Java内部类-2(静态内部类)

内部类一般分为两种:静态内部类和非静态内部类。

1. 什么叫做静态内部类

static声明的内部类称为静态内部类。静态内部类在行为上就是一个顶级类,它嵌套在一个顶级类中以方便打包。

和静态方法一样,静态内部类不能直接引用外部类的实例变量和方法,只能通过对象的引用来使用它们。

public class TestNest {
    private String abc="123";

    public String getAbc() {
        return abc;
    }

    /**
     * 静态内部类
     */
    static class NestClazz {
        public void test() {
            //需要创建外部类对象
            TestNest testNest = new TestNest();
            System.out.println(testNest.abc);
            System.out.println(testNest.getAbc());
        }
    }


    public static void main(String[] args) {
        //使用静态内部类
        TestNest.NestClazz nestClazz=new TestNest.NestClazz();
        nestClazz.test();
    }
}

2. 为什么存在静态内部类

静态内部类在行为上本身就是一个顶级类,那么为什么要使用静态内部类呢?

比如A,B两个类,B有点特殊,虽然可以单独存在,但只能被A使用。那么此时应该怎么办?若是将B并入到A中,复杂性提高,搞得A违反单一职责,如果B独立,又可以被其他类依赖,不符合设计的本意。若设计为A.B,其他类就不能依赖B了。

静态内部类没有必要单独存放一个文件,并且它只能被所在的外部类使用,并且它可以直接被用于 外部类名+内部类名获取。

3. 静态内部类案例

静态内部类一个典型的使用案例便是建筑者设计模式,而lombok插件中,使用@Builder注解,便可以为POJO类增加建造者模式。

源代码:

@Builder(toBuilder = true)
@Getter
public class Address {
    private String address;
    private String phone;
}

编译后的class代码:

public class Address {
    private String address;
    private String phone;

    Address(String address, String phone) {
        this.address = address;
        this.phone = phone;
    }

    public static AddressBuilder builder() {
        return new AddressBuilder();
    }

    public AddressBuilder toBuilder() {
        return new AddressBuilder().address(this.address).phone(this.phone);
    }

    public String getAddress() {
        return this.address;
    }

    public String getPhone() {
        return this.phone;
    }

    /**
     * 静态内部类。该内部类只能被外部类使用。
     */
    public static class AddressBuilder {
        private String address;
        private String phone;

        public AddressBuilder address(String address) {
            this.address = address;
            return this;
        }

        public AddressBuilder phone(String phone) {
            this.phone = phone;
            return this;
        }
        
        //真正创建对象
        public Address build() {
            return new Address(this.address, this.phone);
        }
        
        public String toString() {
            return "Address.AddressBuilder(address=" + this.address + ", phone=" + this.phone + ")";
        }
    }
}

测试方法:

public class Test {
    public static void main(String[] args) {
        //而实际上我们创建的是一个静态内部类对象
        Address.AddressBuilder addressBuilder = Address.builder().address("a").phone("b");
        Address build = addressBuilder.build();
    }
}

4. mybatis与静态内部类

若类B只能被类A使用,并且不希望将类B并入到类A中(会导致类的复杂性提高)。也不希望将B独立,会造成项目的冗余,便可以使用静态内部类,来尽可能的提高代码的可读性。

但是代码可读性提高的同时,如何进行mybatis的赋值?

POJO类:
将People对象中的Certificates(证件)信息抽取为一个静态内部类。

@Getter
@Builder(toBuilder = true)
public class People {
    /**
     * 编号
     */
    private String id;
    /**
     * 姓名
     */
    private String name;
    /**
     * 证件信息
     */
    private Certificates certificates;

    /**
     * 证件信息静态内部类
     */
    @Getter
    @Builder(toBuilder = true)
    static class Certificates {
        /**
         * 证件编号
         */
        private String certNo;
        /**
         * 身份证正面照
         */
        private String certBeforeImg;
        /**
         * 身份证反面照
         */
        private String certAfterImg;
    }
}

普通方法的赋值:

    public static void main(String[] args) {
        People.Certificates certificates = People.Certificates.builder().certNo("1273821653821").certAfterImg("a.img").certBeforeImg("b.img").build();
        People people = People.builder().id("001").name("tom").certificates(certificates).build();
        System.out.println(JSON.toJSONString(people));
    }

对象中的属性为其他对象,此时我们需要自定义返回参数:resultMap

而此时对应关系为1:1,我们需要使用association来完成映射。 额搜神a神


    
    
      
        
        
        
    



相关参考

Mybatis关联查询使用内部类接收

你可能感兴趣的:(Java内部类-2(静态内部类))