在面向对象编程中,接口
是一个重要概念,它是一种契约
,它定义了对象应该具备的方法。一个接口
可以有多重实现,它的所有实现都必须满足接口
所有约定的方法。并不是所有编程语言都有接口,例如在C
、Python
、Ruby
中是没有内置的接口机制,但在大多数编程语言中都有接口
的概念,一般用interface
来标记。
Java
和Go
都是有内置的接口
的机制,但在接口实现上却不尽相同。这些区别主要是接口定义、接口实现、约束机制和应用场景等方面,下面就这些不同进行逐一比较。
接口定义
两者在接口定义上区别不大,都是通过interface
实现的。
在Java
中接口的定义:
public interface Shape {
double perimeter();
double area();
}
在Go
语言中接口的定义:
type Shape interface {
Perimeter() float64
Area() float64
}
接口实现
在Java
中,接口实现类必须通过implements
关键字明确实现的接口,这是一种显式
的声明,将实现
和接口
绑定,也就是说要实现一个接口就必须依赖这个接口。
class Circle implements Shape { // 显式声明实现Shape接口
@Override
public double perimeter() {
// TODO Auto-generated method stub
}
@Override
public double area() {
// TODO Auto-generated method stub
}
}
而在Go
中,并不需要将接口
和实现
做显式
的绑定,只要一个类型包含了接口所定义的方法,并且输入和输出参数一致,那么这个类型则自动满足这个接口
,即表示它实现了这个接口,也就是隐式
实现。
type Circle struct{} { // 自动满足Shape接口
func (c Circle) Perimeter() float64 {
}
func (c Circle) Area() float64 {
}
约束机制
在Java
中,一切皆对象,所以也只有类(class)可以实现接口,基本的数据类型(如:int、long)等均不支持实现接口。
但在Go
中就不一样了,可以说任何类型均可实现接口,包括基本类型(int
、bool
等)、map
、slice
,甚至函数
都可以实现接口
。
必要时,使用函数
来实现接口,便可快速满足业务场景,代码简洁灵活。这是一个函数
实现接口的例子:
type ShapeFunc func() (float64, float64)
func (f ShapeFunc) Perimeter() float64 {
p, _ := f()
return p
}
func (f ShapeFunc) Area() float64 {
_, a := f()
return a
}
另外,在多接口
扩展上,两种编程语言的的实现也有所不同。
在Java
中,一个类可以同时实现多个接口,多个接口以,
分隔,并且接口之间还可以继承:
public interface Drawable {
void draw();
}
// 实现多个接口
class Circle implements Shape, Drawable {
@Override
public double perimeter() {
// TODO Auto-generated method stub
}
@Override
public double area() {
// TODO Auto-generated method stub
}
@Override
public void draw() {
// TODO ...
}
}
// 接口继承
public interface Drawable extends Shape {
}
而在Go
语言中,一个类型实现多个接口,只需要实现多个接口的所有方法即可,多个接口可以组合
成一个新接口:
type Drawable interface {
Draw()
}
type Circle struct{} { // 自动满足Shape接口
func (c Circle) Perimeter() float64 {
}
func (c Circle) Area() float64 {
}
func (c Circle) Draw() { // 自动满足Drawable接口
}
// 组合
type ShapeAndDrawable interface {
Shape
Drawable
}
最后
接口
在编程中的主要作用就是降低耦合、约束行为、提供可扩展性和可维护性。在Java
中显式
的定义接口,增强约束性,提供清晰的接口实现结构。在Go
语言中,则是通过隐式
的方式实现接口,更强调行为
的一致而非类型,接口和实现没有依赖关系,较为灵活。