2.接口有什么用接口有什么用,这个问题在初学Java时一度困扰着我,查阅资料时对于接口的太多解释又让像我这样的小白一脸懵逼,一些专业术语不仅不能帮助理解,反而让人望而生畏。不知道其他人怎么觉得,反正作为一个理工男,尤其作为一个新手的时候,我看到一大串的概念就头疼,我比较喜欢直接看例子。
2.1继承和规范的作用:
定义了一个动物接口(interface Animals):
public interface Animals{ public String voice();//动物的叫声}里面只有一个抽象方法voice(),即动物的叫声,只有方法头,没有实现。接口要求实现它的类必须实现其所有的抽象方法。于是有两个用户定义的类猫和狗,动物有多种,猫和狗是其中的两种,所有我们在它们中分别实现猫叫和狗叫的方法。一个狗类(class Dog):
public class Dog{ @Override public String voice(){ return "汪汪"; }}一个猫类:
public class Cat{ @Override public String voice(){ return "喵喵"; }这样就有个问题了,既然接口只有方法头,而这些方法头在实现类中又要写一次,岂不是多次一举。难道只是为了规范化?即强迫使用这个接口的类必须使用带这些方法头的方法?当然不只是这样。实现类实现接口,就像子类继承父类一样,有继承关系。比如在一个测试类中定义一个方法来知道一个动物是怎么叫的:我要知道猫叫就得这样写:
void foo(Cat c){ System.out.println(c.voice());}我要知道狗叫就得这样写:
void foo(Dog d){ System.out.println(d.voice()); }这样,每多一种动物,就得往类中新增一个方法,这样是非常不利于更新和维护的,而且会大大增加代码量。但是如果把猫狗的行为抽象化,即猫叫狗叫都是动物叫,这样不管方法foo的形参是哪种动物,都能得到他的叫声,代码如下:
void foo(Animal a){ System.out.println(a.voice());}这样,测试类只有一个方法foo,但是我传的参数既可以是Cat对象,也可以是Dog对象,因为实现Animal接口之后的猫类狗类都是Animal类,而且猫狗都会叫(即猫类狗类都“被迫”地实现了voice这个方法)。2.2行为参数化:行为参数化是什么?简单说就是把一种行为作为方法的形参。不理解没关系,看个例子就知道了:
比如,女朋友跟我说想吃红苹果,我就需要一个方法去判断超市的苹果是不是女朋友喜欢的苹果:
void judge(String color){ if(color.equals("红")) System.out.println("是我要的苹果"); else System.out.println("不是我要的苹果");}但是如果女朋友要求突然提高,说喜欢大的红苹果,那我就需要更改之前的方法,参数需要多一个“大小”:
void judge(String color,String size){ if(color.equals("红")&&size.equals("大")) System.out.println("是我要的苹果"); else System.out.println("不是我要的苹果");}这样,每当女朋友改变要求的时候,我们都需要改变原来的代码,这通常是不被允许的,因为它破坏了代码原有的结构。也许我们可以把苹果封装成类,这样参数就只要传入苹果的对象就行了。不过即使这样if里面的判断条件还是会改变,这个时候接口(interface)派上用场了。我们定义一个接口GF (girlfriend缩写):
public interface GF{ public boolean islike();}原来的判断方法改成:
void judge(GF gf){ if(gf.islike()) System.out.println("是我要的苹果"); else System.out.println("不是我要的苹果");}这样女朋友给定需求的时候,我们只需要在主程序新建一个匿名类进行传参就可以了,而原方法体不许做任何改变。
//创建匿名类GF g=new GF(){ @Override public boolean islike(){ return color.equals("红")&&size.equals("大"); }}//调用judge函数judge(g);这里创建匿名类的原因是:不必为一个临时使用的类去创建一个专门的文件。对于函数式接口(只有一个抽象方法的的接口),如果知道什么是lambda表达式的话,写起来更简单。看完这个例子再理解行为参数化就容易了,这里就是把“判断女朋友喜欢的苹果”作为一种行为,并将这种行为作为参数传到judge函数。以上就是接口的两种常用方法,也是作为小白经常能碰到的一些使用例子,这里也是我自己开始去理解接口时的心得。关于更多接口的更详细,更专业的解释网上也有很多大佬发表过言论,这里我就不在这班门弄斧啦(哈哈)!如果本文有什么说的不对的地方,也请路过的大佬帮忙指出。