(3) - 抽象类、接口及内部类(图)

---------------------- ASP.Net+Android+IO开发S.Net培训、期待与您交流! ----------------------


个人学习后归纳的知识点,利于整体记忆。

1、  抽象类概述

是什么:含有抽象方法的类称为抽象类,抽象类名与抽象方法用abstract修饰。

 

什么时候用:当多个类中出现相同功能,但是功能主体又不同,这时可以进行向上抽取,抽取时只抽取功能定义,而不抽取功能主体。简单说,只保留方法声明,不要实现体,该方法用abstract修饰。

 

怎么用:

abstract class Fu
{
     abstract voidmethod();//抽象方法,
     void method2(){}//可以含普通方法
}
Class Zi1() extends Fu
{
     void method()
    {
       System.out.println(“子类1”);
    }
}
Class Zi2() extends Fu
{
     void method()
    {
       System.out.println(“子类2”);
    }
}

 

2、  抽象类的特点

(1)抽象类方法一定在抽象类中,反过来说,一个类中定义了抽象方法,这个类便要加上abstract变成抽象类。

(2) 抽象方法和抽象类都必须被abstract修饰

(3) 抽象类不可以用new创建对象,因为调用无实现体的抽象方法没意义。

(4) 抽象类中的抽象方法要被使用,必须先由子类复写所用的抽象方法后,才能在子类建立对象后调用。

(5)如果子类只覆盖抽象类部分抽象方法,那么该子类还是一个抽象类。

(6)当一个抽象类中没有抽象方法,那么这个类的用途仅仅是为了不创建对象。

(7)其实抽象类,除了抽象方法和关键字abstract,与普通类无异,该有的都有,不过其构造函数却不是自己来用的,因为不能创建对象,它是为子类初始化用的。


3、  接口概述

是什么:由interface 修饰,是一系列方法声明的集合,这些方法都没有实现体,并且所有方法声明都是抽象的。


什么时候用:类似于抽象类,但是由于Java只能单继承,当我们在子类有父类时还需要多个父类时,这时考虑用接口。


怎么用:

interface A//接口
{
   abstract voidmethod();
   void method2();//默认被abstract修饰
}
class B implements A//实现方式
{
   void method(){}//必须复写所有接口方法
   void method2(){}
}


        接口定义时,格式特点:

        (1)接口常见定义:常量,抽象方法

        (2)接口中的成员都固有修饰符:

        常量:public static final

        方法:public abstract


4、  接口的特点

(1)  接口中的成员都是public修饰的,常量少写些关键字会自动补上,方法也是,不过建议写全。

(2)  当接口中的常量赋值后,不可再修改。

(3)  接口不能创建对象,因为全是抽象方法,需要被子类实现,覆盖锁有接口方法,子类才可以实例化。

(4)  类不能多继承,但可多实现,extends继承用,implements实现用,implements后可接多个接口名,用逗号相隔。

(5)  接口和接口之间可有继承关系。

 

5、  接口与抽象类的区别

我将其部分对比整理成一张表,如下:

   对比项   

   类间关系   

成员

   成员权限   

   定义功能   

   结构关系  

抽象类

单继承

抽象和非抽象方法,成员变量

自由

基本功能

is-a

接口

多实现

只有抽象方法,成员常量

只能public

扩展功能

like-a


6、  内部类

(1)  概述

内部类:顾名思义,定义在一个类内部的类,它的载体类称外部类,内部类作为外部类的一个成员存在,内部类可为静态,可用private和protected修饰,而外部类只能缺省或public修饰。

 

何时用:当描述事物时,事物的内部还有事物,该事物用内部类来描述。内部事物在使用外部事物的内容。


(2)  访问规则:

① 内部类可以直接访问外部类中的成员,包括私有。

         之所以可以直接访问外部类中的成员是因为内部类中有了外部类中的引用,格式为:外部类名.this.成员名。


② 外部类要访问内部类,必须建立内部类对象。

体现如下:

class Outer
{
    private int n =1;
    class Inner
    {
        int n = 2;
        void fun()
        {
            int n =3;
            //若不写Outer.this.会取局部变量的值,代码作用域的规则
            System.out.println("Outer.this:"+Outer.this.n);
            System.out.println("Inner:"+n);
        }
    }
    public voidshow()
    {
        //外部类访问内部类,需建立内部类对象
        Inner in =new Inner();
        in.fun();
    }
}
 
public class Test
{
    public staticvoid main(String[] args){
        Outer out =new Outer();
        out.show();
    }      
}

③ 内部类被定义在局部时:

     不可以被成员修饰符修饰。

      可以直接访问外部类的成员,因为还持有外部类的引用。但是不可以访问它所在的局部中的变量,只能访问被final修饰的局部变量。

class Outer
{
    void fun()
    {
	final int x=3;//局部变量加final可访问
        class Inner
        {
             void Inner fun() {
                System.out.println(x);
         }
     }
     //必须给内部类实例化来调用,因为它不再是外部类的成员
     new Inner().Innerfun();
}
}
public class Test
{
     public static void main(String[] args){
     new Outer().fun();
     }
}


(3)  访问格式

①当内部类定义在外部类的成员位置上,而且非私有,可以在外部其他类中直接建立内部类对象(不过很少用)。

如下格式:

外部类名.内部类名 对象名 = 外部类对象.内部类对象;

Outer.Innner in  =new Outer().new Inner();


②     在内部类成员位置上,就可以被成员修饰符修饰。

如:private:将内部类在外部类中进行封装。

     static:内部类就具备了静态的特性,看下面静态内部类的介绍。

           

7、  静态内部类

被static修饰的内部类


特点:只能直接访问外部类中satatic成员。

当内部类中定义类静态成员,该内部类必须是static。

当外部类中的静态方法,访问内部类时,内部类也必须是 static的才行。


访问方式:

class Outer
{
static class Inner//静态内部类
{
     //内部类定义了静态方法,内部类必须是静态的
     static void fun()
    {
         System.out.println("内部类静态方法!");
     }
     void fun2(){
         System.out.println("内部类非静态方法!");
     }
}
public static void Outerfun()//外部类静态方法
{
     //外部类的静态方法只能访问静态的内部类
     new Inner().fun();
}
}
 
public class Test
{
     public static void main(String[] args){ 
     new Outer.Inner().fun2();//该语句访问内部类非静态成员;
     Outer.Inner.fun();//访问内部类静态成语
    }
}


8、  匿名内部类

特点:

(1)  没有名字的内部类,其实就是内部类的简化形式。当内部类只用一次就可以采用这种形式。

(2)  前提:内部类必须继承一个类或者实现接口。

(3)  匿名内部类是一个带前提的匿名子类对象,或者带内容的子类对象。


匿名内部类的格式:

    new 父类名或接口名(){覆盖子或父类要覆盖的成员}.方法

interface Inter{
    abstract publicvoid show();
}
 
class B{
    void fun1(){
        new  Inter()//匿名内部类
        {
            int n =3;
            publicvoid show()
            {//需复写的方法
                System.out.println("匿名内部类! n = "+n);
            }
        }.show();//复写后可调用
    }
} 
public class Test
{
    public staticvoid main(String[] args){
        new B().fun1();
    };
}


匿名内部类的使用场景:

除了为了简写一个单独匿名子类对象,也可当参数传递,

当函数的参数是接口类型引用时,如果接口中的方法不超过3个。可以通过匿名内部类来完成参数的传递。

---------------------- ASP.Net+Android+IO开发S.Net培训、期待与您交流! ----------------------

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值