接口
接口
/* 这个类中除了抽象方法,里面其他什么都没有,
当一个抽象类中的方法全部都是抽象方法的时候,
这时候可以将该抽象类用另一种形式定义和表现,就是接口 interface,即特有的抽象类
-- 表面相像
定义接口使用的关键字不是class,是interface -- 表现形式变了 编译后还是class文件
接口除了有抽象方法,还定义全局常量。
对于接口中常见的成员包含全局常量、抽象方法。而且这些成员都有固定的修饰符
全局常量:public static final
抽象方法:public abstract
由此得出结论,接口中的成员都是公共权限的,权限都是最大的
抽象类搞个类去继承你,如果是个接口,就实现你。为什么叫实现?接口里面的方法全是抽象的,要全部去实现,对于抽象类有些东西是不需要实现,有些非抽象的可以直接继承使用,不用实现
类与类之间是继承关系,类与接口之阿金是实现关系实现。
*/
abstract class AbstractDemo(){
abstract void show1();
abstract void show2();
}
interface Demo(){
/*
static final 不写,会自动帮你加上,所有的东西都是固定,可以简化但是阅读星极差
NUM不加修饰可能不知道他是变量,不知道他可以被接口调用,很有可能覆盖错误,用非public权限覆盖可能会报错。
*/
public static final int NUM = 4;//int NUM = 4;
public abstract void show1();//void show1();
publicabstract void show2();//void show2();
}
/*
接口不可以实例化,只能由实现了接口的子类并覆盖了接口中所有的抽象方法后,该子类才能实例化,否则这个就是一个抽象类
*/
class DemoImpl implements /*实现*/ Demo(){
public void show1(){
}
public void show2(){
}
}
class InterfaceDemo(){
DemoImpl d = new DemoImpl;
d.NUM = 3;//因为NUM是fina,不能被改变
System.out.println(d.MUM);//都对
System.out.println(DemoImpl.MUM);//
System.out.println(Demo.MUM);//
}
/*
接口的出现解决了很多实际的问题,比如继承的时候,java不支持直接多继承,因为会出现调用的不确定性,所以java将多继承机制进行了改良,在java中变成了多实现
即一个类可以实现多个接口。
多继承解决的什么问题?为了提高子类的功能,提高扩展性,
一个类可以实现多个接口,我们注重的是这个事物应该具备什么样的功能,至于这个功能要怎么用,由子类来明确。
如果子类认为父类定义的功能已经符合我的要求了,直接拿来用。如果父类的功能不满足还得重写,一样的,
只不过接口必须要重写。如果接口定义了方法,实现接口就认为这类事物具备该功能,
-- 多实现的体现
*/
interface A{
public int/*void*/ show /*showA*/(){
}
}
interface Z{
public void show /*showZ*/(){
}
public int add(int a,int b);
}
class Test implements A,Z()/*多实现*/{
/*这个方法即覆盖了A中的show,又覆盖了Z中的show*/
public void show(){
}
public int show(){
}//这俩方法不能同时存在,名字都一样,调用的时候是返回的哪个。
public int add(int a,int b){
return a+b+3;
};
}
class InterfaceDemo(){
//如果取创建Test子类对象,调用show的时候有不确定性嘛?
Test t = new Test();
t.show();//多继承有方法体,就是因为有方法体导致了运行的结果不一样,现在实现没有方法体了,就更安全了,可以实现多个
}
/*
一个类在继承另一个类的同时,还可以实现多个接口
*/
class q{
public void method(){};
}
/* 具备q的功能,又想要其他的功能,想扩展Test2的功能
继承一个属于一个体系,又使用接口形式扩展其他功能。
接口的出现避免了单继承的局限性,一个类只能有一个父类,但是却可以同时实现多个接口,扩展性强大。一旦想扩展就想使用接口。
接口与接口之间是继承关系
*/
class Test2 extends q implements A,Z{
}
interface CC{
public void show ();
}
interface MM
public void method ();
}
interface QQ extengds CC,MM{
public void function();
}//接口与接口之间是继承关系,而且接口可以多继承,多继承的缺陷是在方法体上,接口没有方法体。接口可以多继承,多实现。用的不多,但是确实存在了。
clas WW implements QQ{
//必须实现3个方法
public void show (){};
public void method (){};
public void function(){};
}
/*
接口的特点:
笔记本电脑举例:
很多功能被封死到笔记本里面。只要一点开机基本就能使用了。触摸屏不太爽,喜欢鼠标。
把电脑拆开,把接触摸屏的线断掉,接到鼠标上,搞个连接封起来。
笔记本到哪鼠标就到哪,很不方便。这种方式没有继续使用
后期笔记本公司,做触摸板单独分两线,留了两个口,下一次不要拆电脑,直接买鼠标,但是要匹配口的型号,直接插入使用。插口就是接口
接口的概念很大,对外暴露的都是接口,比如笔记本的usb口,提供插口,想要用鼠标必须买一个相符的插口,就是笔记本提供的对外的规格。
对外提供的规格就是他的一个特性。
有了USB口,是不是大大降低了鼠标和笔记本的关联性,以前是焊接在里面,现在留接口直接插就可使用。降低了笔记本和鼠标的紧密程度,降低了他们的耦合性。
耦合性:扣得很死,降低紧密程度,但是有关系,他们符合同一规则。
usb不仅可以查鼠标吧,凡是usb的都可以插,提高了笔记本的功能。插入一个硬盘,电脑内存变大了,这就是提高功能扩展性
接口是对外暴露的规则。
接口是程序的功能扩展。
接口是出现降低耦合性。
接口可以用来多实现。
类与接口之间是实现关系,而且类可以继承一个类的同时实现多个接口
接口与接口指之间可以有继承关系。
笔记本的设计,大大提高了笔记本的利用率。这个接口找一大圈没有合适的接口,谁会用呢?usb口少,买电脑的人可能也会少。接口太小,插不上。
电器都有插头,因为国际化组织定义了规则,必须符合规则才能使用。
主板上预留插头,你是什么设备不知道,但是我知道你想要主板运行的设备,我就留有插头,照着插头做就行了。厂商实现规则,也降低了耦合,以前是焊接,现在是插入
厂商自己做自己的板卡,往上一插不就完事了吗,为啥主板上要有自己的声卡网卡?为了集成,买设备以后,这个功能已经成为了大众化所需的基础功能,主板不仅仅要保证对电脑的独立运行,而要保证一些提供基本功能,直接加进来。主板对常见的网卡或者声卡进行了默认实现,哥们自己提供的规则,网卡厂商用的也是我的规则,可是我发现网卡芯片功能需求很大,做的时候网卡芯片,把规则都实现完了。设备走的是电路,我做芯片走电路。如果觉的默认不合适,就自己重新实现这个功能。
凡是提供功能扩展性,必须提供接口,没有接口就会死,需要重新开发。如笔记本待触摸板,只有电源,啥孔都没有,过两天想加内存没有口,不能扩展,只能再做个笔记本了。我要留个口,随时可以增加设备。
*/
/*
接口和抽象类的异同点:
抽象方法是放抽象类还是放接口呢?他们很相似?
相同点:无论抽象类还是接口都是不断向上抽取而来的。描述的不具体
不同点:
1、 抽象类需要被继承,而且只能单继承
接口需要被实现,而且可以多实现
2、 抽象类中可以定义抽象方法和非抽象方法,子类继承以后可以直接使用非抽象方法
接口只能定义抽象方法,必须由子类去实现。
3、 抽象类的继承是 is a 关系 所属关系:在定义该体系的基本共性内容,抽象类共性的基本的内容
接口实现时 like a 关系,在定义该体系的额外的功能
例子:学员有学习功能-基本功能,抽烟是额外的功能,实现抽烟的额外的接口
类在确定体系,接口在提供额外功能,接口确定扩展。
犬按功能区分:
导盲、缉毒犬
但是他们都剧本基本功能,
问题领域分析:
不停地问题领域中,有不同的分析设计方式。不要固化。
比如学员都有抽烟的功能
*/
abstract /*这个到底是定义类还是接口呢*/ class 犬{
abstract void 吼叫();
}
class 导盲犬 extends 犬 implements 导盲{//继承了导盲就,就有导盲功能,继承了犬就有吼叫功能,但是不能多继承,如果这俩变成接口了就可以多实现。但如果都变成了实现会是什么样子
//对于导盲犬最根本的是犬,具备犬的功能,犬可能定义一般方法或者抽象方法,只有类可以做到接口做不到。在定义的时候,犬应该是一个类。定义节本功能。而导盲应该是犬的额外功能
public void 吼叫(){};
public void 导盲(){};//不写导盲接口直接写导盲犬不就完了吗,这么弄程序扩展性,本身有共性为什么不抽取,不利于扩展。。凡是具备导盲的都可以去,总比导盲猫上,导盲狗上,一个个来的好,导盲是这些物种额外抽取的功能。
}
abstract class 导盲 extends 犬{//本身有共性,为什么不抽取,扩展性不好
public void 吼叫(){};//不只狗具有导盲,所以把导盲功能直接抽离出来
}
interface 导盲 {
public void 导盲(){};
}
/*
接口的应用
我们先做程序,分析的时候先定义这些规则,我们程序再使用这个规则。
你什么也没有,怎么使用这个规则?遍布所有,判断是否有,没有则跳过。
定义接口也不知道后期有什么?不管你有什么设备,你想要你的设备被我使用,就要符合USB口,否则用不了。。
厂商是不是就要按照接口做,他们是不是就是这个接口的实现。而实现的是后来的,虽然实现是后来的,但是设备之前就已经正常使用
接口定义规则使用规则,另一部分实现规则
还有个多态。
我们再描述的时候,会先描述一些规则,目的是为我们建立的程序工作自然,对外提供一种规则,好处降低日后程序和我的程序的耦合性
当我们定义规则了以后就已经再使用规则了,没有给我传递符合该规则的对象,我就规则就不动
日后你按照我的规则做,日后你就能用的上。
笔记本电脑使用运行
*/
/*
* 笔记本电脑使用
* 为了扩展笔记本的功能,但日后出现什么功能设备都不知道
* 定义一个规则,只要日后出现的设备都符合这个规则就可以了
* 规则再java中就是接口 interface
* 前期写的程序,就因为提供规则,可以使用后期进来的设备。
*/
public class BookPC/*public class BookPC*/ {
public static void main(String[] args) {
// useUSB(null);
useUSB(new UPan());//功能扩展了
useUSB(new UsbMouse());
}
//引用类型的都指向对象,但是接口不能创建对象,接口的子类覆盖了接口的方法,可以实例化,接口指向的是子类的引用对象
//接口类型的引用,用于接收(指向)接口的子类对象
//使用规则
public static void useUSB(USB u/*函数中的一个参数,是接口类型参数,变量是由接口定义的*/) {
u.open();
u.close();
}
//一年后。买了一个U盘。描述事物
}
/*//增加了功能笔记本就要不断修改,比如新增一个内存,还有在笔记本类中添加一个功能
public static void useMouse(Mouse m){
m.open();
public static void main(String[] args) {
useMouse(new Mouse());//用起来很麻烦,并且不利于扩展,且后期不知道会出现什么设备
}
}*/
/*
* 不知道会有什么设备,但是他们都有共性,插上就开启,拿下来就关闭了
*/
public interface USB { //前期暴露的规则
public void open();
public void close();
}
public class Mouse {
public static void main(String[] args) {
}
public void open() {
// TODO Auto-generated method stub
}
}
public class UPan implements USB{
@Override
public void open() {
// TODO Auto-generated method stub
System.out.println("开启");
}
@Override
public void close() {
// TODO Auto-generated method stub
System.out.println("关闭");
}
}
/*
这些设备和电脑的耦合性就降低了吧
*/
public class UsbMouse implements USB{
@Override
public void open() {
// TODO Auto-generated method stub
System.out.println("UsbMouse 开启");
}
@Override
public void close() {
// TODO Auto-generated method stub
System.out.println("UsbMouse 关闭");
}
}
public class Mainboard {
public void run() {
System.out.println("main board run ...");
}
//扩展性差,不断修改原来的代码,这些都是后来的,我们不知道会有什么,
//具体功能不知道,我们对外提供规格,按照我的规格做,你功能我就可以用,接口
public void useSound(SoundCard c) {
c.open();
c.close();
}
//擴展型搞了,多態
//但是如果想讓它運行,就要new個對象,不傳聲卡,聲卡與主板永遠沒有關係,是不是要修改源代碼了,如果加網卡修改代碼了
//我想實現不修改源代碼就可以增加設備
//不在使用声卡,无论什么设备都符合这个接口
//如果什么都没插呢
public static void usePCI(PCI p) {
if (p!=null) {
p.open();
p.close();
}
}
}
public class NetCard implements PCI{
@Override
public void open() {
// TODO Auto-generated method stub
System.out.println("網卡打開了。。");
}
@Override
public void close() {
// TODO Auto-generated method stub
System.out.println("網卡關閉了。。");
}
}
public interface PCI {
//无论什么时候来都给个开启给个关闭
public void open();
public void close();
}
public class SoundCard implements PCI {
public void open() {
// TODO Auto-generated method stub
System.out.println("打开声卡。。。");
}
public void close() {
System.out.println("关闭声卡。。。");
}
pci1=utils.SoundCard
pci2=utils.NetCard