EffectiveJava笔记(三) 类和接口

13. 使类和成员的可访问性最小化

对于成员(域 方法 嵌套类和嵌套接口)有四种可能的访问级别, 下面按照可访问性递增顺序罗列出来:

  • 私有的(private): 只有在声明该成员的顶层类内部才可以访问这个成员

  • 包级私有的(package-private): 声明该成员的包内部的任何类都可以访问这个成员, 从技术上讲, 它被称为”缺省访问级别”, 如果没有为成员指定访问修饰符, 就采用这个访问级别

  • 受保护的(protected): 声明该成员的类的子类可以访问这个成员, 并且, 声明该成员的包内部的任何类也可以访问这个成员

  • 公有(public): 在任何地方都可以访问该成员

14. 在公有类中使用访问方法而非公有域

如:
class Point {
    public double x;
    public double y;
}

要被替换为:
class Point {
    private double x;
    private double ;

    public Point(double x, double y) {
        this.x = x;
        this.y = y;
    }

    public double getX() { return x; }
    public double getY() { return y; }

    public void setX(double x) { this.x = x; }
    public void setY(double y) { this.y = y;}
}

Java平台类库中的java.awt包中的Point和Dimension类违反了”公有类不应该直接暴露数据域”的告诫, 它们使不值得效仿的例子, 总之, 公有类永远都不应该暴露可变的域,

15. 使可变性最小化

不可变类只是其实力不能被修改的类, 每个实例中包含的所有信息都必须在创建该实例的时候就提供, 并在对象的整个生命周期内固定不变, Java平台类库中包含许多不可变类, 其中有String, 基本类型的包装类, BigInteger和BigDecimal, 存在不可变的类有许多理由, 不可变的类比可变类更加易于设计, 实现和使用, 不容易出错且更加安全

为了使类成为不可变, 要遵循下面五条规则:
1. 不要提供任何会修改对象状态的方法
2. 保证类不会被扩展: 即是防止子类化, 一般做法是使这个类成为final的
3. 使所有的域都是final的
4. 使所有的域都成为私有的, 防止客户端获得访问被域引用的可变对象的权限
5. 确保对于任何可变组件的互斥权限, 如果类具有指向可变对象的域, 则必须确保该类的客户端无法获得指向这些对象的引用, 并且永远不要用客户端提供的对象引用来初始化这样的域, 对于有些类而言, 其不可变性是不切实际的, 如果类不能被做成是不可变的, 仍然应该尽可能地限制它的可变性

16. 复合优先于继承

继承是实现代码重用的有力手段, 在包的内部使用继承是非常安全的, 子类和超类的实现都处于在同一个程序员的控制之下, 对于专门为了继承而设计并且具有很好的文档说明的类来说, 使用继承也是非常安全的, 然而继承打破了封装性, 子类依赖于其超类中特定功能的实现细节, 超类的实现有可能会随着发行版本的不同而有所变化, 如果超类发生了变化, 子类可能会遭到破坏, 所以子类必须要跟着其超类的更新而演变

17. 要么为继承而设计, 并提供文档说明, 要么就禁止继承

对于为了继承而设计的类, 唯一的测试方法就是编写子类, 如果遗漏了关键的受保护成员, 尝试编写子类就会使一楼所带来的痛苦变得更加明显, 如果编写了多个子类, 并且无一使用受保护的成员, 就应该把它做成私有的

18. 接口优于抽象类

抽象类允许包含某些方法的实现, 但是接口不允许, 为了实现由抽象类定义的类型, 类必须成为抽象类的一个子类, 因为java只允许单继承, 所以, 抽象类作为类型定义受到了极大的限制

接口优点:

  • 现有的类可以很容易被更新, 以实现新的接口

  • 接口是定义混合类型的理想选择: 一个类可以实现多个接口以表现出不同的类型

  • 接口允许我们构造非层次结构的类型框架: 一个类可以实现多个接口以表现出不同的类型, 接口是可以多继承的, 一个接口可以继承其它接口以构造非层次结构的类型

接口缺点:

  • 接口一旦被公开发行, 并且已被广泛实现, 想在改变这个接口几乎是不可能的, 必须在初次设计的时候就保证接口是正确的, 如果接口具有严重的缺陷, 它可以导致API彻底失败

19. 接口只用于定义类型

有一种接口被称为常量接口, 如下

public interface Constants {
    static final int MAX_VALUE = 255;
    static final int MIN_VALUE = -255;
}

常量接口模式是对接口得不良使用, 类实现常量接口, 对于这个类的用户来讲并没有什么价值, 反而会使他们更加糊涂, 如果在将来的发行版本中, 这个类不再需要这些常量了, 他依然必须实现这个接口以确保兼容性, 如果非final类实现了常量接口, 它的所有子类的命名空间也会被接口中的常量所”污染”

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

编码兔

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值