00:00
那么关于这个接口呢,咱们就告一段落了啊,接着的话呢,我们来看看这个爱圭509,这个叫inner啊,实际上呢,这儿呢,我们要讲的是类的成员之五,叫做内部类啊,这块我们再来回忆一下,咱们说到的整个呢,这三章也是我们这个第二个阶段啊,讲面向对象的三条主线,第一条主线呢叫类及类的成员啊,这呢,我们说属性方法构造器一一梯队的。呃,第二梯队呢,有个代码块,这个重要性呢,就差一些了,然后现在我们要讲的是这个内部类啊,这块我们要讲的实际上这个内容呢,是在这儿的。啊,那随着这个内容呢,讲解完成了,其实基本上啊,咱们这个面向对象的话呢,就算是啊稍微的告一段落了,说后边这边还有内容吗?后边的内容的话呢,其实可以看到是基于我们讲的类也好,接口也好之外的一些补充内容了,比如呢,我们后边这个枚举类,这就是一种特殊的类了,呃,注解属于我们,呃基于类接口之外的另外一个补充的结构。啊,就是我们像这个一个圈叫override是吧,这呢叫注解了,来稍微的说一说它的使用,后边这个呢,叫做包装类啊,这呢也属于一种特殊的类了,所以后边呢就是属于补充的一些内容了,最后呢,我们再讲一下idea中的这个快捷键和如何debug啊,这就属于大家实际开发当中使用的这个功能。
01:14
所以呢,基本上内部类的讲解完成,我们面向对象呢,可以简单来说呢,就画了一个小的句号了,诶把这三章里边我们讲的面向对象的内容呢,大家梳理梳理,OK。好,那我们来看一下这个内部类,首先呢,从这个重要性上来讲。从这个重要性上来讲呢,内部类呢,它的重要性呢要低一些了,诶咱们平时开发的时候,自己呢,定义内部类的机会呢比较少,更多的时候呢,就是我们在看一些源码的时候呢,发现呢,他很多时候使用的都是内部类了,诶所以呢,在出现源码中内部类的场景的时候呢,我们得知道他怎么用的就可以了。诶,所以呢,对他对大家的要求呢,就比较低一些了啊好,那么首先第一个概念说什么是内部类啊。来,回过来,我们看一看。其实呢,非常简单,那就是这样的一个概念啊,所以呢,我们将一个类A定义在另一个类B里边了啊,那么里边的这个类A呢,就称为叫内部类了,然后这个外边这个类B呢,就称为呢叫外部类。
02:13
相当于以前的话呢,我们没有这个内部外部的说法,其实呢,就相当于原来我们写的类呢,都属于叫外部类了啊。哎,现在呢,只不过在它里边又放了另外一个类啊,这就叫做内部类。就这个概念很简单啊,那么紧接着的话呢,我们就提到说人家为什么需要在一个类里边又定义另外一个类呢,是吧,有什么必要性吗?这呢就提到说为什么需要那个类,哎,我这儿呢,写了一个理由,大家看看啊。说具体来讲啊,说当一个事物A的内部啊,还有另一个部分需要用一个完整的结构B呢来进行描述的时候,而这个内部的完整的结构B呢又只为外部事务A呢提供服务,不在其他的地方单独使用。那么这时候呢,完整的这个结构壁呢,我们最好呢,就使用内部类。啊,这个说的比较清晰哈,说这个类A呢,这呢就是个类了,然后这个类B的话呢,首先呢,它是一个完整的结构,你用一个变量去刻画呢,还不足以能够刻画它。
03:08
它里边呢,可能还有更丰富的一些属性啊方法呀,是吧,这样一些结构,所以说这个结构B的话呢,也得用一个类来进行刻画。啊,那你完全可以呢,说类呢就放到这儿,说类B呢,就跟它并列的去写个类B啊这是没问题的,是可以这样写的,所以这呢,也导致我们平时开发的时候呢,咱们可能比较少去定义内部类了,可能我们就写成并列结构了。但是对于这个源码来讲呢,它设计起来就会更加的规范和标准一些啊,他明确发现这个B呢,只在A里边去用。那不妨呢,我就把这个B这个类呢,就声明在A里边了,表明呢我只在A里边用,那么这个B呢,就是内部类。那么这样呢,哎,我说总体来讲呢,又遵循了叫高内聚和低耦合的面向对象的开发原则。这个词咱们在哪讲过?对,封装性的时候说过是吧,封装时我们提到了一个呃这两个词儿,另外呢,还提到一句话呢,说把该隐藏的隐藏起来,该暴露的暴露出去是吧,在这里边儿这个类B的话呢,因为你只在类A里边用嘛,所以呢,我们就相当于写成类不类了,一定程度上呢,就实现了一个隐藏的特点。
04:16
在这呢,就理解成叫高内聚和低耦合。啊,对内啊,我们去定义相关的结构,对外的话呢,呃,只提供你需要的这样的一些呃方法啊,该暴露的暴露出去,不该暴露的话呢,我就定义在内部啊大家呢,体会一下这里边儿这个情况啊。好,仍然就是属于我们讲理论层面的一些这个内容。OK,这就可以了,那么具体来讲呢,说诶能不能给举俩例子啊啊让我们感受一下是吧,哎这呢也可以了啊这个内部类的话呢,我们首先呢,诶提到一个这个比如说叫thread。这个thread呢,是我们后边讲的叫多线程的一个类。这个类呢,呃,它内部。啊,内部声明了啊,一个类叫做state。
05:01
啊,内部呢,声明了stay类这个类的话呢,来表示叫现成的生命周期。啊,这个state就要状态了是吧?呃,一个线程的话呢,它有生命周期,比如说你是刚创建的呀,你还是正在运行啊,还是这个线程阻塞了呀,还是你这个线程死亡了呀。是吧,这块呢,我们都理解成是他的生命周期的几个状态,那么这个状态呢,其实就是这个state这个类的几个对象了。这个时候呢,这个我就把它呢,哎,刚才说的这个状态呢,定义在这个类里了,然后这个类的话呢,因为你就是表示在线上的生命周期,跟别的类也没关系。也就是说呢,这个类呢,只供他用。所以我们就把它呢,定义在了它的内部。啊,这里我就不用看这源码了啊,诶这大家知道这个就行,哎在呢举一个例子,比如说呢,我们后边呢,会讲到这个集合,集合里边呢,有一个接口呢,叫做map接口。哎,这个map啊,接口中啊,或者是咱们具体来讲的话呢,叫做哈希map也行啊哈,Map呢,是属于这个map接口的具体一个实现类了,这个哈希map这个类当中,他就声明了一个。
06:10
诶,声明了啊一个什么呀,叫做no的这个类。哎,它呢来表示。哎,我们封装的这个key和value。诶我这一写呢,大家可能有点懵哈,这个后边呢,我们讲这个map的时候呢,诶会讲哈,说这个哥们儿呢,它是一个容器,跟咱们说的数组一样哈,数度是容器,它也是容器,但是这个容器呢,它有个特点,就是它存的都是这种诶建指对特点的数据了,比如说这个张三考了这个70分,诶李四呢考了80分啊这个王五呢考了90分,然后这里边儿呢,左边呢这个呢就叫做K。然后这个呢,就叫做value。他存的是一种都是特点的数据。啊,那这种数据的话呢,咱们说呢,实际上啊,你看的呢,像是两个数据,其实呢,它是一个对象的两个属性,哪个对象呢,就是这个node类的对象,所以呢,我就把这俩呢,其实是封装成一个对象了。
07:08
啊,就是大家我这样一说,你就一听就行了啊,后边我们再详细讲好,那么这个对象呢,就是node类型的,那由于呢,我们这儿呢,是哈希map来存对象了,也就是说你这个note呢,是不是只供我用啊。别人也不用是吧,诶所以这块呢,我们把这个no呢,也定义到哈西map的内部了,就是证明呢,就说只有我用别人不用。哎,这不就跟我们上面说的这个就匹配起来了吗。哎,就大家体会一下这个事儿就可以了啊好,那么关于这个内部类的话呢,呃,具体的这个分类呢,怎么看呢,其实也非常简单,大家就参考我们讲的变量的分类。变量的话呢,我们说按照在类中生命的位置呢,分成叫成员变量啊和局部变量。诶,那么这个内部类的话呢,也同样的道理,我们就分成了叫诶成员内部类。啊,以及呢,叫局部内部类。N下什么叫成员内部类?
08:01
就是直接生命在web类的里边是吧。哎,外部类的啊,里边啊,相当于呢,你在一些方法呀,构造器呀,他们的外边啊,这叫做成员内部类啊,在局部类不类,就类似于叫局部变量一样,这个怎么着呢。所以我们可以呢,叫声明在方法内。或者叫构造器内,或者叫代码块内啊,这样的这种内部类。啊,生命在这些的啊,内部类。就称为呢,叫局部内部类,类似于局部变量一样。好,那么成员变量,当然咱们讲的时候呢,它呢又可以,呃,根据呢,是否使用死代这个修饰呢,分成了叫类变量和实例变量是吧。所以这块呢,我们也是用是否用死在这个修饰呢,把这个成员这边的呢,也又分了一下,诶分成了叫做使用。哎,使用这个呆的一个修饰的。
09:02
哎,那这个呢,我们称为叫静态的成员内部类。哎,很好理解是吧。啊,那你没有使用磁代求呢,就是非静态的成员内波类呗。哎,不使用带修饰的,就是非静态的成员类。啊,说白了就是还想体现这个成员内部类啊,你这个类呢,是跟这个外部类呢的类相关,还是跟你这个外部类的这个对象相关。这不就体现静态和非静态的区别吗?有点懵啊,咱们前面讲说静态的成员面料。是不是跟类相关?所以叫类变量,非静态的成员变量。Name呀,Age啊,是不是跟对象相关?诶,那我们叫实例变量了哈,这个也是一样啊,就是你这个非静态成序类类,你是跟你这个web类的对象相关呢,还是跟web类相关的是吧,这块的有个区分。OK啊好,那么这个成员内部类的话呢,呃,这个呢,这个我们就稍微的先写一下啊,它呢具体要分成呢,就称为呢,叫匿名的呃,成员内部类啊。
10:05
还有那叫非匿名的。哎,成哎,程远不累了,局部累不累呗。哎,累不累,诶这个呢,我就先这样一写啊,咱们呃,稍微的你看一下,讲到这的时候我们再细说就可以了。好,那么提到这个事儿的话呢,我们下边呢,就先来写例子了。啊,这个不妨呢,我这个就叫做altered class啊,这个我们顺带我就写个test了啊。哎,这么着。好,然后呢,咱们把这个知识点往这边放吧。啊,这个我们往左边放啊呃,下边的话呢,我们就先来定一个,比如说叫person。诶,这个person的话呢,我把它看作叫web类吧。那就是因为你里边呢,写这个内部类了啊。好,那么这个内部类的话呢,如果直接就这块儿开始写了,那就属于叫成员内部类。非内部又分成静态的和非静态的。这个咱们就那就整整俩吧,哎,首先呢,来一个叫static的,来来一个class写个什么呢。
11:06
诶注意啊,这块的话呢,我们说呢,呃,它不一定是人的。一部分,你比如说我这边定一个类,这个类呢叫做大脑。啊,大脑的话呢,你用一个变量刻画呢,感觉差点意思,我们用一个类来刻画是吧,哎,这个类呢,比如说有一些属性啊,有一些方法呀,是吧?哎,当然这个你注意哈,这个大脑呢,确实实打实属于我们人的这个身体的一部分了哈,说这叫内部类,其实呢,你说我这块定义成一个狗。能理解不?你说这个啊,不是说人身体里边有个狗啊。对,咱们想刻画的仅仅是说。这个狗呢,只会让这个人去用是吧,所以呢,我们就不把它定义在外边儿了,所以呢,你体会一下啊,不是说这个它属于这个人身体的一部分啊,不是这种关系了。对,不是属于这种关系,只是说呢,它只供这个使用是吧,为了形象哈,我这块我就定义成一个狗了,方便大家呢,就是稍微理解一下啊,这个呢,我们称为呢,叫做静态的。
12:05
诶,成员累不累,好,再来一个非静态的。哎,非静态的成员类不对,好这块我们就直接呢来一个class啊,来一个鸟吧。比如是吧,这个呢,表示就只供这个person类使用的这样一个类类啊,仅此而已。好,这个呢叫做成员的啊,那除了成员之外呢,我们说还有这个局部的,局部的话呢,比如说啊public avoid啊,就写一个方法了啊,这个大家体会下就行,在这个方法内部,我们去定义的叫做局部内部类。比如我这块啊,Class class一个我叫inner啊,CLASS1啊,比如就他了,这呢是可以的,然后呢,构造器也可以啊,这public一个person。哎,在这里边呢,你再来一个啊,一个叫an inner。比如这个二。这样的。
13:00
哎,这都算啊好,那问一下,你说这个呢叫inner class1,我这呢也能叫inner class1吗?说是重名的。对。对,因为它是不是生命在我们这个大框里了,是吧,出了大块呢,是不是就失效了。哎,所以这块你定义成重名了也没关系啊。好,这呢叫代码块啊,代码块里边呢,我们去定义的。哎,这也叫做局部内部类。哎,这都算当然呢,我们下个问题说,诶这有啥用是吧?呃,这个咱们稍等一等再说这个事儿啊好先知道从这个格式上来讲的话呢,就是这样的一个情况啊,呃,先把这个事儿呢先明确一下,刚才呢,我写的这呢都算是有名的。哎,都是非匿名的。啊,匿名的这个场景呢,其实就好比是我们比如说实现一个接口的匿名实现类,那个实现类呢,你写到相应的这个方法里了,那其实就是一个局部的一个情况,而且是个匿名的。这个咱们一会儿再说好,那么整个这个内部类这块呢,相较于我们前面讲的属性啊,方法呀,构造器来讲,这个重要性呢要低很多了,所以关于内部类这块呢,大家不用花太多精力去研究,我们这块呢,只需要说明这样的几个问题就可以了啊第一个问题就是关于这个叫诶成员内部类的一个理解。
14:10
啊,因为这种场景呢,我们稍微来讲啊,内部类呢,首先用的不多,那在内部类这个场景下的话呢,成员内部类算是用的比较多的。就是内部类在不多的情况下,就是这个意思啊,比如这个内类的话呢,我们使用频率呢,可能只有5%。是吧,在5%里边儿呢,可能4.8%,哎,它都属于这个叫成员内部类。所以呢,我们这块呢,既然讲到内部类了,那我们这块主要看一下这个成员内部类我们该如何呢去理解好,这是第一个问题,那第二问题的话呢,我们需要呢,去了解的就是成员内部类呢,它分成了两种,静态的和非静态的,我们需要关注的就是如何创建。哎,这个叫成员内部类的实例。那这呢,自然而然就分成了叫静态的成序链位和非静态成链位。这俩呢,有区别。
15:00
因为呢,一个是随着类的加载而加载,一个是随着对象的创建而加载。啊,区别就在这儿了,好,这是我们说的这个事儿啊,好,然后下一个问题的话呢,就是对于这种成员类类来讲啊,我们里边呢,可以定义方法了,然后呢,方法里边呢,如果你想使用web类的这种成员。这时候在调用上呢,有没有什么要求和讲究啊,所以这块就说到了,说呢如何在。哎,成员啊,内部类中,哎调用啊外部类的结构啊。这儿呢,我们要给大家说一下。那这个都是讲的关于这个成员内部类的,最后呢,我们再来关注一下啊,叫局部内部类的使用。啊,它的一个基本使用。好,这个所谓的基本使用呢,一会儿我们讲到它的时候呢,再说啊这呢,我们就诶说清楚这个事儿了啊好,那么这儿呢,就是我们关于这个内部类这块呢,咱们要讲的这样的几个知识点,大家呢,也只需要关注这几个事儿就足够了啊那首先呢,我们来看第一个问题。
16:01
关于成员内部类的一个理解啊,这个对应的就是我们下边这样的一个问题了。哎,怎么去理解这个类不类啊,其实这块呢也不难,哎这块我们可以说呢,首先啊,从类的角度看。成员累不累?你也好歹是个累呀。哎,所以这块你就具备类的一些特点,好,那另外一个角度来讲呢,你这个类啊,你是一个成员,是外部类的一个成员,那就是我们从外部类的成员的角度看你呢,又能怎么着。呃的成员的啊,这个角度看是吧,诶这块呢,我们就把这两个事儿呢,其实说清楚呢就可以了啊。好,那么首先来看啊,说从一个类的角度去看,我们这个成员累不累。从一个类的角度来看哈,既然你是个类了,我们就说呢,哎,你内部呢。可以是不是声明属性啊,方法呀,构造器呀,代码块啊,诶是不是还能累不累。
17:00
还能有一层层往里套了,只不过一般没必要是吧?啊等结构。啊,既然你是累了,你不就有能力做这个事儿吗?没问题是吧,好,那从一个类的角度上来看的话呢,呃,类我们讲过是不是有继承性。那你说这个内部类它能有负类吗。那一定可以,或者换句话说呢,你没有写负类。是吧,那就是吧。对啊,所以说呢,这个从类的角度来看呢,说这个,呃,此内部类呢,可以声明父类。啊,然后呢,可以实现接口都可以类,就一个接口可以好多个,就跟我们讲的原来类的这个特点都一样。啊,这是没问题的啊,啊,这是一个。嗯,然后的话呢,它是一个类。这个类的话呢,呃,如果你看前面我们讲过类的一些修饰哈,如果呢,想表达这个类呢,它不能有此类。
18:01
哎,是不是又可以用final修饰是吧?哎,这呢可以使用final修饰。哎,表示的就是你这个类呢,它不能有子类了啊,这我简单写一下啊,你看我这加个final。没事儿是吧,哎,就表示你没有此类的意思了,好,那么我们讲类的时候呢,还提到过哪些修饰呢。他这个权限是吧,诶那个权限呢,其实咱们一会儿呢,我写到这儿合适一点啊。哎,关键字。哎,抽象的事儿是吧,好这个类呢,如果是个抽象类呢,意味着它不能实例化是吧,诶这块你看我们加一个啊叫abstract是不是也可以。所以这块呢,表示呢,就是它呢可以使用。Abstract来进行修饰啊,没问题。好,那么这样的话呢,哎,我们是从一个类的角度呢来看,哎这呢都是OK的啊。好,那这呢就过了,然后接着的话呢,我们从这个,哎,从外部类的一个成员的角度来看,他现在是一个成员了。啊,比如说你想象成它这个方法,我们说过,诶外部类的一个方法里边方法内部呢,可以调用啊,当前类的其他的属性和方法。
19:06
啊,那这呢,就意味着你是一个外部类的成员了,那我们说呢,就在内部。哎,是不是可以调用。外部类的。呃,属性或者是方法或叫外部的这个结构啊。比如说这个属性啊,方法呀是吧等。哎,这样的一个结构。哎,这个呢,一会儿我们要说的事,不就是说这个事儿吗。这个点。啊,这呢是从一个成员的角度来看的哈,呃,然后的话呢,刚才大家提到了说关于这个权限的问题了哈,权限的话呢,我们用public修饰呢,显然是没问题的,呃,我要是不写public呢,这不就默认权限吗?以前我们讲这个所谓的类,其实以前咱们讲的都是web类,这个web类的话呢,除了用public,还有这个默认权限修饰之外呢,不能写成private是吧。这显然报错了啊,那你说我们现在这个内部类了。方法的话呢,可以写成private,那此时他呢。
20:03
哎,它也可以加private了。因为你是个成员嘛。哎,成员的话呢,就可以用四种权限来修饰了啊,所以这儿呢,我们说呢,诶除了使用。哎叫啊public以及呢,我们说这叫缺省。哎,权限啊,修饰之外。哎,还可以使用。哎,我们说的叫private和protected呢,进行修饰。嗯,Protected来修饰这个呢,就是体现了你是个成员这样的一个特点啊。好,那除了这个之外呢,我们还讲过一个关键字呢,能够修饰类的内部成员的。对,叫做斯代IC是吧?哎,那这时候呢,我们说这个死呆IC的话呢,也可以用来修饰这个类,这不就是自然而然的分成叫静态的和非静态的了吗。啊,你要是一个web类的话呢,死在这个是没有意义的啊。哎,所以这块我们说呢,诶可以。
21:01
来使用那代立可能来进行一个修饰诶。可以了,好,那基本上就告一段落了啊,所以呢,关于这个成员内部类的话呢,它是什么样的情况,其实呢,由于我们有已经有这个类的一个基础了啊,一个积累了,所以大家呢,再去理解这个事儿的话呢,其实就比较清晰这个事儿的杨一写,其实大家呢,对于这个创业内部类这块呢,其实就。哎,理解的就差不多了哈。好,那么关于第一个问题,搞定。哎,就这样啊。这个大家呢,不用死记硬背,你说我得背出这四条,这是三条,没必要啊,每一个呢,我一说你都能理解就行。好,接着说如何创建成员内部类的实例。也就是说,我现在想创建dog的对象和word的对象。啊,怎么创建是吧,这个呢,咱们把这个权限呢,稍微的就比如说就给大家放开了啊好,我想创建这两个实例,我在哪创建呢?我在上面这个测试类这块来创建吧。哎,在这要写啊,在这里边儿,首先第一个我们去创建。
22:03
啊,这个叫静态的。哎,成员内部类的。哎,它的一个实例,也就是说我们创建了一个dog的实例,接着呢,我们在创建了一个word。诶波的话呢,这个是非静态的。这个我们看怎么去创建啊,呃,先创建这个dog吧,Dog呢,你看它这个静态的哈。那就意味着它是随着类的加载而加载了。你说我要创建dog的对象,我还需要创建person的对象吗?哎,注意就不用了。哎,就不用了啊,哎,那你这块我直接去new一个dog吧,哎,这个又差点意思,因为你这个dog呢,毕竟你没有直接对外暴露嘛。你要想掉dog,你得看看人家person。让不让是吧,你在人家内部嘛,所以这块你得这样写哈,我得去new person里边的这个dog。哎,注意得这样写了。或者换句话说呢,我这有个外部类,我这叫do,你是不是还有可能也有其他一个类,假如叫A里,A里边是不是也有个dog是吧,你要直接说你有个dog,那不行了,你得说清楚是谁理的呀。
23:09
所以我们得有外部类点啊,这样的情况好,那自然而然的话呢,前面你要是声明就叫个dog的话呢,是不是也有这样一个起义了。那要是万一A类类的dog呢?所以这块你得说清楚,是person里啊。Dog。哎,这呢,就创建好了。哎,创建好以后呢,假如这个dog里边有相应的这种方法的话呢,是不是就可以调了。Public就是这个我们叫。叫吃吧。吃吃吃骨头啊。吃。比如来一个骨头啊好,那这块呢,我们拿着这个,哎,到个点儿啊,掉这个eat方法是不是他就可以看骨头了是吧。哎,这个没问题,好,这就相当于实打实呢,确实是有一个这个对象的啊。好,这个就完事了,然后接着我们来看下边这个啊,我现在要创建这个bird的对象了。这个bird,注意它不是静态了。
24:02
非静态的结构是不是都得依赖于外部类的对象?所以呢,要想创建bird对象了,你注意你就不能像上面这个写法了,哎,也就是说当你想你说我就new一个啊,Person点这个鸟是吧。哎,拟完以后的话呢,你看这块声明啊,还写成叫person.bird。哎,那这时候呢,他就报错了啊。这个不行。啊,这个我们得注释一下啊,哎,因为呢,你不是静态的啊,所以这个呢是报错。那你得去创建person的对象。先把对象先造出来。到处地区了啊,那接着怎么写?哎,接着这个写法的话呢,大家很容易写错啊,这个这样写p1.new。Word。可能跟你想的不太一样哈。然后呢,声明,哎,就是刚才这个。这个呢是一个正确的。
25:01
啊,可能有的同学会这样想,我你又一个P一点是吧。注意,这样写法是错的啊。哎,别拗谁点啊,就是P1的这个对象去调这个new。啊,这样啊,所以这个别把new写在前面了啊,这个错误的我就删了啊,要不把错误的记住了。坏了啊,这样写好,那这个bird里边呢,如果也有一个一的方法。啊,这个呢叫哎。这个鸟儿。啊,觅食吧。啊,吃虫子也行。那这个呢,我们写完之后呢,哎,接着回过来啊,我就通过这个a bird点啊第这一的方法来。Run一下。你看这就没问题。OK啊行,那这样的话呢,我们就来清楚这个第二个问题了,说如何创建成员内部类的实例,第一种啊针对静态的,第二种针对于非静态的,这个呢,我们就说清楚了。
26:00
啊,说清楚了啊,之前呢,咱们有同学不是写代码就写错了,什么意思啊,以前呢,咱们还没有讲类部类的时候啊,有的同学呢,这块写了个类,这块呢,比如说写了个person,本来呢是两个并列的类,结果一不小心呢把这个大括号啊给整到。这块了。把这个person呢,给整成个内部类了是吧。然后呢,上面这块呢,直接上来就new一个person,诶怎么不行呢。啊,因为你这是内部类了,你这个时候呢,还是个非静态的嘛,是吧,你得怎么着,要想new person,你还得把这个外部类的这个对象先造一下。这就很多同学为啥以前出错了找不到原因,因为你把这个person你给洗到里边了是吧。哎,那这儿呢,其实你是两个并列的类。啊,这是以前有同学写错的,你知道原因是啥啊?好,这个呢,是我们说的这个第二个知识点,然后第三个啊,第三个说呢,如何在成员内部类当中调用外部类的结构。啊,来看这个事儿哈,这个呢,其实正常来讲呢,嗯,没什么特别的,呃,关键呢,就是有的时候呢,会出现这种所谓的比如说重名的属性。
27:02
方法的这个又重这个这个重名了啊,有这样的问题,比如说在这个person里边啊,大家看哈,我定义了一个死string性的name。啊,为了方便起见哈,这个比如我就写上假设就叫Tom了是吧?好,这是一个名,然后这个以鸟为例哈,这个鸟的话呢,是不是也可以定一个性的name。是吧,哎,我们这个人类的话还有个属性啊,我叫in特型age,哎,我这写上值叫一吧,这个鸟呢,没有这个属性。哎,那么关于内和A的调用呢,因为呢,我这里边也有个name,所以导致呢就会有点麻烦了啊,哎,我这呢先来一个,比如说这叫一个show方法吧。好,这个事方法里边注意看啊,如果呢,我直接呢,去打印一下这个age哈。先看行不行。你发现它可以直接掉的。那么这个呢,我按住CTRL键一点,哎,其实掉的就是外部类的这个属性。哎,说明呢,你看是可以直接写的哈,但是问题就在于我们关于这个name的一个调用。
28:01
哎,我如果呢,这样就写了内幕。也不报错,我按住CTRL键一点。点到这儿了是吧。这是假设,咱们为了方便起见呢,我赋个值啊。比如叫。呃,啄木鸟。诶,它是吧,好,那么这时候呢,我们其实能看到呢,它掉的其实是啄木鸟啊。或者再换句话说呢,比如我这个位置,我就故意的哈,我再声明一个name啊。那这时候呢?是不是成行参了?哎,对哈,好,那我这块故意的啊,就加了个内幕,那我现在如果想调这个啄木鸟怎么办。对啊,前面呢,咱们讲过是不是用this来去区分,哎,这个星三和乘以变量是吧?哎,这个this呢,指的是鸟还是person?诶是谁,你就看这个Z写在哪个方法里了,谁掉兽谁就是Z,兽呢是人家鸟里的方法,所以呢,这个Z呢就是鸟啊好,那么刚才这个问题来了,我现在怎么去调的这个name。
29:06
毕竟重名了嘛。嗯,这个时候呢,你可能会想说这是类里的。但是呢,毕竟这个内幕属性不是。静态的吗?不是静态的这块怎么整。修了super呢,这个大家可能,呃,联想到我们讲接口的时候呢,这里边呢,在这个里边,这我是不是用修了。但是你注意这个修复呢,毕竟我们这个sub class跟这个compare a b它是有这种。继承关系也好,时间关系也好,他的地位是不平等的,是吧?哎,是你实现人家了啊啊,这是上下上下级的关系,你想调上面这一级的叫super了,那你现在呢,跟人家不是这个子服类的关系啊,鸟可没继承人。成鸟人了是吧?啊,那这个不能写super啊。是person这个它里边的这个实力的这个内幕属性。所以这个呢写Z。
30:01
啊,其实这些点的话呢,大家以后你要是自己想写一门语言,差不多也得这样写呗。要不你咋整啊是吧,OK啊好,这个呢,其实我们就能够去做这个区分了,这呢是关于属性这个层面的,那咱们就试着来调一下这个受啊。那回到这块呢,咱们拿着这个B的点调这个寿这块呢,因为你有行参,所以得赋个值,比如来一个这个。呃,比如说黄鹂是吧。好,这个呢,我调的是这个方法。啊盯一下啊来下边我们去做这个运行。哎,做一个run。哎,这就出来了,好,这个A的话是一,那因为这块我们复值是一,所以这个呢,就是我们外部类的这个值啊,这个呢,我调它是因为没有什么冲突啊,所以直接写呢,其实也没毛病,然后这个name呢,就你这个行参,所以呢这个就是黄鹂了,这个呢就是你自己的这个成员变量鸟子里的这个叫啄木鸟。然后下边这个呢,指的我们是web类的这个传变量啊,这个叫Tom。
31:02
啊,没问题啊,那这里边儿这个age的话呢,如果我们要补全的话呢,是不是应该补这个。没问题是吧,诶所以这块我们可以说呢,这个位置啊,相当于它呢,要省略了。哎,这个声明啊。啊,这个呢,我们体会一下,这儿呢,是我们关于这个叫。方法啊,方法里边调属性的事儿,那我们在这个内部类里边呢,说能不能调外部类的这个方法呢。比如我这有个一的方法,这呢是鸟呢吃虫子,那人的话呢也有方法。我就写到看清楚啊,写这儿了。这个一的方法呢,是咱们人里边定义的啊。呃,人呢,吃。嗯,吃鸟啊。人吃饭吧。啊,你说这的话呢,我想起来一个细思极恐的一个事儿啊,说这个小孩的这种教材是吧。这个小孩不是有这个教材嘛,这个都是一些漫画之类的哈,里边儿呢,比如这个小猫啊小狗啊,这个就是这个请客吃饭是吧?啊说有一次这个小鸡啊请他的这个朋友来家里吃饭啊,一桌子菜,结果里边上面还摆了一块鸡肉。
32:09
这个就差点意思是吧。这挺吓人的哈,嗯。好,这个呢是我们是在这个person这个里边呢,我写了一个方法。OK,然后呢,我再来一个啊。来,Avoid,我来个兽医。然后呢,我这块呢,如果这样写一个一的方法呢,你会知道啊,我们自己也有一个哈。那这个意思是谁的?是不是显然是自己的?啊,因为这里边儿还显然呢,省略的其实是Z4点嘛。就是这块呢,没加C点,相当于呢,还默认的就是C点,所以这俩呢是一个事儿啊,那如果你现在想调用web类的一的方法怎么办。对,有了上面这个概念以后呢,是不是就得这样写了。哎,这就没问题啊好。测试一下啊。哎,Bird点受益啊,哎,我们做一个run。
33:01
哎,你看这时候就是啊,就是前面这两个的话呢,都是你自己的。嗯,然后呢,后边这个呢是person,哎,没问题。那么这块呢,我们也就说到这儿了啊,就是关于这个内部类的话呢,它是有能力来调用外部类的这样的一些结构的。啊,这块调的话呢,其实还有一些细节,我没有多说什么细节啊,就是我们这是静态的啊。静态这里边儿呢,你在调的时候呢,你考虑这种非静态调合不合适,然后非静态的话呢,这个内部类呢,你调外部类里边静态也好,非静态好,其实都没问题。啊,这些事儿的话,其实就太细了。啊,大家就没必要呢追的这么细了啊,我们这些事儿呢,就略掉了啊,OK,好,这个呢,我们就把呃第三个问题说如何在成员内部类中调用外部类的结构,以这个bird为例,我们就说了一下。哎,大家体会体会就可以了。好,那下边的话呢,我们来看一看关于内部类啊,这个内容的后边一个知识点,叫局部内部类的一个使用啊,这呢也算是我们要讲解这个内部的内部类的最后一个知识点啊,关于局部内部的一个使用这块呢,我们再去新建一个类去说明。
34:06
啊,我叫做alter。Class test1啊,这样。好,然后在这里边儿的话呢,我们去说明一下。哎,叫局部啊,内部类的一个使用。啊,体会一下啊,局部类不类啊,那就相应的你得定义在像方法呀,构造器啊,代码块当中的啊,那更多的时候呢,我们是在方法里边建的,所以不妨呢,我这块就拿方法来说了,这呢我们定义一个方法啊叫METHOD1,在这个方法里边的话呢,我们去声明一个内部类啊,比如说class一个A。哎,这个呢,就称为呢,叫局部内部类了。啊,局部。累不累是吧,没啥问题啊,然后这里边儿你去声明属性,声明方法就可以了。哎,可以声明属性方法等是吧,这样的一些结构啊,嗯,这块大家你要看的话呢,似乎觉得说好像。
35:01
是要干啥用是吧。不是很明确哈,诶,那么实际上开发中呢,就这种泛泛一起的机会呢,其实不多。啊,我们见到的会是什么样场景呢?是这样的这个场景,哎,我这块来说一下啊,开发中的这种场景。开发中呢,我们一般见到的会是这样一个情况,比如说我调用这个方法的时候呢,需要你返回一个实例,这个实例的话呢,呃,是一个什么类型的呢?诶我这个呢,叫做comparable类型的。这个呢,我们就get一个instance。哎,就他啊这个comparable的话呢,你点开它其实呢是个接口。啊,这个呢,大家没有见过,你就忽略掉啊,这个你就当没写它,这其实是一个新特性叫泛型啊好,我现在需要你返回一个接口的实例啊,那这个接口的话呢,要想造实例,你得先提供一个实现类,那这个实现类呢,我就写到内部了。所以呢里边呢,就提供了实现了啊,这个comparable接口的实例。或者首先呢,是提供了实现了这个接口的一个类啊。
36:04
好,那这就这样写了,说class一个,比如叫my comparable。让他俩去一下这个comparable。那这个comp的话呢,是个接口里边有创方法,哎,这个out回车再回车再回车,这呢就是你重启的这个方法。当然这个重写方法这个细节我就不多说了啊好,这呢就相当于提供了一个它的实现类,这个类呢,你写到方法里了,这是不是就是局部类不类。哎,就他啊,然后在这个位置呢,我们再去return一下,哎,我叫new一个叫my comparable就可以了。哎,当我们去调离方法的时候呢,我就返回了一个它的时间类的一个对象啊。哎,这个是我们会见到的这种场景。啊,这个呢,稍微注意一下啊,那这个的话呢,我也可以写成了,这仅仅是叫方式一啊。还可以呢,把它呢,再进一步的做一个。啊,这个简化啊。放12。
37:00
哎,方式二怎么着呢,你看此时呢,这个接口的实现类是有名的。这个对象没有名。相当于呢,你可以理解成呢,我们这儿是提供了。啊,这个接口的实现类的匿名对象是吧。实验类有名叫my compable,对象没名啊,这块直接就给返回了。那我现在能不能说提供了接口的匿名实现类的匿名对象呢?哎,匿名实现类的匿名对象,哎,我把这个呢就注释了。怎么着呢?直接我就称了。我就牛了。就哎comparable了,你看我这块写的话呢,我一回车他就全给我弄好了哈,我就自己来吧。Comparable是吧,那很显然呢,这个comparable呢,这个接口这也没构造器啊,诶我们这块呢,是表示叫匿名了啊,所以呢,从形式上来讲,用接口呢来充当,然后在这个小括号后边呢,来一个大括号。来体现呢,你是个实现类,然后把接口里边这个抽样方法呢,还给重写了。
38:04
就这么着一下。就可以了。看看能不能看懂。啊,这时候呢,我们理解成呢,是这个接口的一个实现类的对象,这个对象呢,也没有名叫匿名嘛。是吧,就这样或者这个大家感觉说有点整的有点太猛了。要整不动,整不动的话呢,咱们先这样啊,提供了接口的匿名实现类的有名的对象。有名的对象。Comparable c。把它呢。拿到这儿。然后这块呢,就return c呗。真的是一个有名的对象哈,那接着呢,再过分一点,不就刚才写的那个匿名对象吗?哎,实现了接口的匿名,实现类的匿名对象。
39:01
哎,那这呢,就把刚才这个事儿呢,我再重新在这儿。哎,Return直接在return这个吗。CTRLC粘过来,哎,这个我们就注释一下它。哎,这是我写了这么几种方式吗?说诶咱们前面讲这个接口的时候,我写过四种方式是吧。还差一种啊。下一种呢,就是其实你要从这个理解上角度来讲的话呢,那应该是往前放了。哎,这块大家可能会有点儿懵哈,这个你看提供了接口的事件类的对象也别匿名了。是不是就有名啊?这咋弄?其实就还是这个呗。这个实验类这块有名。实验类呢,叫他找个对象,对象也有名。我叫M。你有一个my compar,这不有名吗?然后return m呗。这是最标准的一种写法。然后呢,我们可以呢,接下来哎,从这个类的角度,从对象的角度都可以让他们匿名。
40:04
是不是就接着一一步步越来越抽象是吧?呃,最抽象的其实就是这样一种格式。啊,这个大家稍微的体会体会啊。好,哎这呢,我们把上面这个我们return呢,啊把这个注释一下,哎,这不走这个return吗。啊,这就可以了啊。好,那么这时候大家你看哈,现在呢,我们是直接拗了一个实现类的对象了,你可能觉得说,诶,这有内部类吗?没看到内部类啊。这我们讲这个方法里边讲累不累呢是吧。你要说看这呢,这叫累不累?嗯,这个话呢,这也算干累不累,因为明显你看到这个名了。那这算是有内部类吗?有。只不过这个内部类的话呢,匿名了。啊,顺带着我还直接还造了个对象了。你就看不清晰了而已。但是有啊。
41:00
这块呢,大家会觉得有点绕,通过这个呢,我再说一个知识点。啊,先放掉它,咱们先回到刚才的这个位置。这个位置呢,我们有个类叫person类,这里有个叫dog类,这里有个bird类对吧。这有三个类啊,这是两个成员,好,咱们看一看最起码文件。咱们现在讲的是这个零九的啊。这个里边的。零九的是不是这儿啊。啊,这块我们打开,嗯,打开它的这个物理磁盘文件上的这个位置啊。好零九打开inner打开好大家看一看这块呢,你可能会稍微有点有点懵啊。嗯。来看一下啊。嗯,方便起见,我就直接这么着了啊。好,这块来看,首先的话呢,我们看这个person哈,咱们说呢,编译完以后会生成自解码文件,像我们说的这个接口会对应着自解码文件类呢,每一个类也会都对应着一个自解码文件,所以呢,从这个角度来看的话呢,首先person类有一个自解码文件,这没问题是吧。
42:05
好,然后呢,我们这里边儿呢,定义了一个dog,定义了个bird,注意这两个类呢,它是person类的内部类,所以呢,我们看到它的磁金码文件呢,是长这个样子的。对,你就是你不能是到点class,因为你那表面是。Person里边的是吧,所以呢,这个person后面有个Dollar符dog person里边个Dollar符叫bird,所以说你是静态的还是非静态的,这个我就不区分了。哎,这是这样子的,所以呢,大家你看到这个结构你得知道啊,这就是表示内不内的意思了。没问题是吧,好,然后的话你会发现呢,诶怎么还有这仨呢。是吧,这仨呢,恰好不就是我们定义的这个局部内部类吗。我在下边儿这块呢,不是写了一个,写了俩写了仨。诶,然后呢,这也是内部类,虽然说叫局部内部类了哈,它也是内部类,所以呢,我们也看到是叫person Dollar,后边呢,是那个内部类。但是此时这个内部类呢,你发现它有个特点。
43:02
他前面加了个123是吧。啊,这个呢,你注意我们局部类不类呢,因为你是放在相应的方法呀,构造器里的是可以同名的嘛。那你都叫inner class,那这块怎么办呢?我前面给你加个标号哈,123,因为呢,咱们在这个Windows里边不能出现同名的这样的文件呀。所以通过这123呢,这不就区分你这个同名的这个局部内部类了。哎,就是这样一个原因。啊,不记着他就可以了。这个呢,包括呢,我们上边这个测试类。哎,测试类这块呢,这不是他嘛,它呢对应的这不就这个吗。就完事了啊,然后的话呢,我们看一下刚才写的这个里边不就这仨吗。是这个吧。这仨啊,这仨怎么去理解呢?回到这儿来。哎,首先这呢,一个叫CLASS1是不是这个。
44:00
没问题是吧,好,然后呢,我们在这个方法里边定义那个A,是不是也算是你外部类里边一个内部类了,诶这个内部类的话呢,虽然说现在诶也没有跟它同名的呀,没有重名的,你万一要以后有呢,所以这块我在写这个A的时候呢,前面也补了个一。其实就表示的这种呢,都属于叫局部的内部类了啊。这不就EA吗?指的就是他。诶好,然后这块你看还有个一点啊。这个对应的是谁呢?一点是不是对应的,就是我们最后的这种写法的。因为呢,你这个没有名啊。没有名,你说我写个啥呢,我也不知道写啥呀,那不好意思,你来个一吧。1.class说的就是它,那从这个角度来看呢,这首先是不是也有内部类了。只不过这个内部类的话呢,是一个方法里边的匿名的没有名,不好意思来个一吧。哎,就这个意思,好,你看我要是把它给注释掉了,我把第一种方式打开。这个打开了,然后呢,我这块呢,我就不运行了啊,直接咱们就编译一下了。
45:01
编译完以后的话呢,我们再回到这个位置上。啊,这时候大家再看一眼哈,是不是这时候你看它就叫这个名了。因为你这时候有名了嘛。就长这样了。嗯,行。这块呢,稍微的感觉有点绕啊,诶其实这块呢,大家呢,就是熟悉一下,第一个就是我们怎么去表达内部类的,呃,资金化文件啊,就通过外部类呢,一个倒符的方式去表达,然后具体这里边呢,其实细节呢,大家听一下就完了啊诶你知道呢,它有一种标准是吧,去表示就行了,这以说呢,具体写代码的话呢,我这里边写的这四种方式呢,诶大家有必要下来呢去掌握一下,因为以后我们写代码的时候呢,可能就诶非常的。这个方便的便捷的就使用方式四了,你要能够看得懂。就行。好,那么关于这个局部内部类呢,哎,怎么使用呢,其实以它为一个典型的,我们就说完了。这个说完以后呢,大家你回过来看谁呢,你看下咱们当时讲过接口,讲过apply,讲过这个USBUSB的时候呢,回到前边。
46:07
啊,大家你看啊,我这是个main方法吧。这个没方法呢,咱们在这个位置哈。你看这个位置呢,我了一。你说这块呢,是不是就算是一个局部内部类了。你不是在这个方法里边写了一个。哎,接口的实现类嘛,只不过这个类没有名而已嘛。这是不是就算是有一个了。上面这个不算,上面这个你这个printer也好,还有呢,我们这个。这个什么camera也好,这是你都写到外边了吧,这个是你对应的吧。呃,而我们第三种方式和第四种方式这个呢,你都是在main方法里边,其实提供了may方法里边的这个类,只不过匿名而已,所以说如果我们要是看这个接口里边的这个子码文件的话。
47:01
是零八吧。哎,看这块儿啊,我们去open in explore。在没方法里面,没方法我们写到哪个类里了。写到这USB test里了啊。USB test这里边啊USB test。啊,这个打这儿是吧。那被开的里边,你看是不是有个一有个二。这个一和二对应的是不是就是我们这里边儿的一个三一个四啊。诶稍微的体会一下这块呢,有点难度,但是呢,刚才我看那个资金化文件这个事呢,大家可以不去关注,你只需要关注代码会写就可以了。啊,真的就完事了,好,那么至此的话呢,咱们关于整个这个内部类这块呢,其实就讲完了。诶大家重点掌握的呢,第一个啊,就是这个内部类理解,第二呢造实例,第三呢,如果叫这个外部类的这个结构,最后这块呢,关于局部内部类这块呢,大家只需要关注代码上会写就行,你拿这USB呢去理解也行,那我们刚才呢写的这个TEST1这里这几个方式去理解可以。
48:09
好,那么内部类这块这个知识点呢,我们就说到这儿,接下来看一下这个课后练习题,这个练习题的话呢,这就留了一道啊,看这一道呢,大家会不会做,哎是这样说的,说呢编写一个匿名的内部类,说呢他继承object,并在匿名内部类当中声明一个方法叫做test打印上。然后调了个方法。呃,写的呢比较简洁,但是呢,呃,应该很多同学会看不太懂。这我们来写一下啊,这个比如就叫object,它这样一个测试了。啊是这个意思啊,说呢,他现在让我们去创建一个匿名的一个内部类。他呢继承一,然后呢多了一个方法,这个类呢,注意是没有名的。你看啊,这个我们稍微的慢一点来的话呢,可以这样来理解,比如说呢,我们要是在这个位置去写的话呢,这个理解成其实是个外部类了,这个类名呢,你随便起。
49:00
比如我叫sub object吧,让他呢,诶你就不用写继承了,因为本身默认呢,就是继承于他的是吧,这个可写可不写啊,他让在这个子类这里边呢,定义一个方法叫做test。CRC。哎,我这呢,我们就定一个方法叫test,这个呢说打印一下这个叫,哎上硅谷。然后呢,我们可以在这个方法里边呢,你可以创建咱们这个叫object这样的一个实例哈。哎,光标放在这儿,Alt回车直接呢,我们就生成这样一个对象了啊,我叫。萨一啊好,拿着这个萨一呢,我们去调这个T方法这块的话呢,应该所有的同学都能看得懂是吧。这块要是说现在看不懂的话,那就麻烦了啊,咱面向对象呢,基本上已经收尾了啊。啊,造个对象调方法,你看再回归到咱们一开始讲面向对象的时候说的是,所以呢,我们首先呢叫创建类。呃,然后呢,设计类里边的属性和方法啊,当然构造器呢也可以加代码块,累不累啊都可以,然后第二步呢,叫创建类的对象,第三步呢叫调属性调方法,这还是跟咱们一开始讲的那三步呢是统一的,以后大家写代码全是这个套路啊。
50:09
但是现在这道问题的时候,你就别给提供名了,整个匿名的就行,而且这个匿名的话呢,通常咱们也就调一次了。所以自然而然的话呢,我们就直接在main方法里边去做这个事了,所以呢,我就写到这儿了,相当于呢,就要提供一个啊,既乘于object。他的匿名子类了是吧。这个提供一个匿名子类,这个子类没有名,你只能调一次,他也让我们去造对象,那我们这块这个对象呢,就直接给他写出来得了是吧,你看我这块怎么去做哈,我首先你得注意。如果要是这样写的话呢,表示我们new的是一个object对吧。好,那我现在object,我在这个位置啊,我加上一个大括号。在这个大括号里边呢,我写上一个这样的方法。然后呢,这就相当于我把这个匿名此类呢对象也给顺带着造好了,这个对象呢有名好名呢写前边注意,那这个名的话呢,因为这个子类都没名了,那你是不是只能是用多肽的方式赋给这个父类了。
51:12
所以我就这样写的。注意,这个时候咱们创建的可不是object对象啊,如果是object对象呢,Object里边也不可能会有test方法,既然你这块你声明test方法了,只能理解成是它的子类啊。哎,这个我们相当于是提供了一个继承于object的匿名此类的对象嘛。这个对象呢,有名。哎,这个对象呢叫obj,然后接下来我们拿着这个obg点去调这个test方法。哎,上面我注释掉了啊,为什么不让掉。为啥不让掉啊?呃,因为我们这个object里边是不是声明是他是吧,根本就没有这个方法是吧。那咋整?啊,怎么着?对,你看正常来讲的话呢,我们现在生命成object的话呢,不让调,按照我们以前的思路,你这呢,确实相当于是个多肽了吧,那必须得转成这个子类的这个类型,然后才能调T,但问题这个子类没有名啊。
52:11
那算了,那咱们就别这样弄了,怎么办啊,这个对象的话呢,我们就也别给起名了,因为起了名也没啥用是吧,我直接在这个位置呢,我就点这个test了。东西就疯了,就是吧,啊,你看它是这样的哈,这样看我new一个object是吧,原来的时候呢,假设我们这块咱就先调个toth吧。这不就表示我们造了个对象,直接调了对象的一个方法,因为我呢都有这个方法,所以我就这样调的啊,只不过现在的话呢,我们怎么着呢,是我呢造了一个object的此类的对象啊,怎么叫此类呢?因为我在大括号里边呢,重启了,呃,是这个多增加了一个方法嘛,这个方法叫test测方法,就它诶我写完以后呢,造的这个对象,你这个对象里边不就有这个方法嘛。既然有这个方法,我不就在这儿可以去调这个test方法了吗?
53:00
哎,所以整个呢,这不就相当于是你把这个方法往这里边儿一写,这不跟上面的一样吗。哎,这样去理解。啊,这就完事了。哎,那只不过这个对象呢,相当于它也是一个匿名的一个场景。这道题啊,简单来说呢,它实际上是我让我们这样来做。啊,这就写完了啊。好,这个写完以后呢,感觉很多同学应该是稍微有点疯了是吧。咱们这个重点呢,其实内部类这块呢,用的不多,但是啊再唠叨一遍,咱们前面讲的这个USB的时候呢,这1234的四种写法呢,这个我们用的是比较多的,在1234里边这个三和四啊,其实就用到了。这个内部类了是吧。哎,只不过都是匿名的方式啊,这个大家稍微体会一下,这个呢,如果说不太行的话呢,我再给大家写一个例子。哎,我再放到这块,我再写个例子啊,这个例子的话呢,如果你听懂了啊,这就相当于是咱叫什么呀,成佛还是成魔就看这一下了啊,看能不能过这一关了啊这个呢,我还写成一个叫alter。
54:02
哎,Class,我写成叫二吧。哎,虽然呢写成这个名了,但是这块我们就把前面提到的一些,不管是接口也好。出羊类也好啊,这块统一的给大家呢,去举个例子。这儿呢,首先拿接口来说。啊,Interface啊,这呢,这个类呢,我就稍微抽象接口呢,抽象一点我就叫A了啊里边呢,我们就public avoid,我写个method。这个抽样方法好,这呢,我们比如说写个main方法。过来啊,那这块呢,是个抽象方法了,咱们按照这个传统的思路来讲,首先我们来一个叫sub a,让他去place implement一下这个A,当然你把这个抽象方法呢,你给他,诶实现一下是吧。具体方法体我就先不写了啊好,然后回到这个位置的话呢,呃,以前的话呢,我们就直接呢叫萨博A啊,去new一个这个萨博A。用完以后呢,你通过A呢去调就行。哎,其实第二段就是你自己重写这个方法了。稍微的写着方法题吧。哎,就这么着,所以执行的话呢,就有我们这个输出。
55:03
这个呢,是我们比较啊,这叫什么标准的这种写法,那实际上呢,这个写法的话呢,哎,我们这就来一个啊举例一是吧,那我们就可以呢,直接去拗一个这个A了。对吧,直接拗这A的话呢,哎,我们可以呢,先给它写上个名,那我就AA就它了,但是这时候你知道接口肯定不能拗,所以呢,我在这个位置呢,就整个大括号把这个方法给重写了,我们理解为呢,就是提供了一个接口的匿名实现类的对象。哎,这个呢,我们叫,哎匿名实现类的,哎呃,匿匿名实现类啊,相当于重写的这个方法。啊,方法叫method是。那就它啊好,这个完了以后呢,我们接着通过这个A1呢,咱们去调这个是不是调的,其实就它吧。对啊,这个呢,这不就跟我们USB里边这个类似的这个场景。啊,然后呢,比这个稍微的。恶心一点儿的啊,这个举例二。
56:01
所以我们就直接我就拗A了,或者我就我就不写了,我直接再把这个结构到这儿。CTRLCCTRLV粘过来,然后呢,这不就你造的这个对象,我不给名了,我就直接在后边去点了。这就我们举例这个二。这就跟我们刚才那写的那个object这个是不是就类似是吧。哎,这是这个场景啊,这个呢,我们去运行这也没有问题。啊,也没问题。啊诶,如果这块呢,我们要是用个名去说的话呢,你可以这样说啊,就是相当于是提供了。啊,提供啊接口啊,匿名实现类的。对象是吧。这个类呢没名,但是这对象有名叫A。而这个呢?哎,匿名实现类的匿名对象,因为这个对象你还想去调方法,这不就直接在后边调吗。那就这个哈,好,那么接口呢,也就这样了啊。接口有这样的,然后呢,我们不是还有抽象类吗。
57:00
接下来啊,说class,一个来一个叫B吧。这个B的话呢,我写成叫abstract。抽象类啊,这个抽象类里边的话呢,可以有抽奖方法,也可以没有,咱们先整个有的啊。我这叫一个method的一吧。An abstract。哎,行。这呢是一个抽类,关于接口的这个情况呢,我就说完了,下面我们来看这个抽象类,抽象类的话呢,其实也存在这样的这个情况啊。好,回过来。举例三啊。这个抽象类的话呢,我们要是标准的写法呢,那自然而然的也是说我class一个叫做sub b,让他呢去一下这个B。然后呢,你这个除法方法,我们把它呢做一个,哎,重写是吧。哎,这个叫sub。没问题,好,然后呢,回过来啊,这块你就sub b一下。
58:02
SB1有点。S1吧,啊,哎一个哎。哎,这样啊。发音得准一点啊,要不有歧义了啊啊调麦一啊,那这时候调的不就你。重写的这个吗。啊,这块我们调用,哎,这不就出来了是吧,这个呢,算是咱们说的比较标准的这种写法,那下边呢,又不标准了啊。哎,举例这个四。但现在呢,我想干嘛呀,我想呢,提供一个既乘于抽象类的啊,匿名子类的一个对象。我就一个直接就毙了。是吧,直接扭一个B,但是B呢,是个抽象类啊。那我就在提供你这个这个此类的同时呢,把这个抽象方法也得重写一下了,所以呢,我们诶咱们慢慢来哈,我现在把它生明成是一个B先这样,然后呢,因为你这抽样类呢,有构造器倒是有,但是呢你有抽样方法,所以呢你在这个小块里边啊,你把这个抽样方法呢给它。
59:04
哎,重写一下是吧。对,或者我们叫实现更标准是吧,反正这种冲要方法呢,我们的重写呢,都称为叫实现了啊好,你把这个呢就去掉。来我们打印一下啊,这个呢,叫继承于抽象类的啊,这个呃子类。啊,然后呢,调用的这个方法。那就它好,那这个呢就写完了,然后呢,我通过这个B点,咱们去调这个METHOD1。哎,就可以了。啊,这个我们去做一个run。哎,这不就出来了是吧,那么这块理解呢,就是相当于我们是那叫提供了继承与抽象类的匿名子类的对象。哎,这个子类没名。哎,对象有名叫B是吧。就他啊好这个呢,我们就调一个方法,诶这块呢,怎么证明你这算是一个子类呢,大家你看哈,我稍微的这样给大家去看一下,这个B呢,我有个方法叫get class。
60:07
这是我们这当中定义的一个方法,就是获取你这个对象所属的类是吧。那么这时候你看我们打印的结果啊。大家看。看能看能不能看懂啊,说这个呢,你看说这个它所属的类是吧,它所属类他竟然说是跟B没关系啊,因为呢,这个类它是没有名的,你写到哪儿了。是没方法理了。所以呢,就是你当前这个类里边的一个内部类了。啊,那因为呢,你是一个方法里边,而且还没有名,我就给你整一个号是吧,你说这怎么是三呢。你前面不还有接口吗。结果我们这儿还整了俩呢,是吧,诶到他这儿就成了这个三了啊。哎,当然这个细节呢,大家就你就了解一下就行,这块不用你特意的去关注哈,关键就是你会写这个代码。啊,这个呢,来了以后呢,我看我再复制一份啊,在它的基础上呢,我再去get一个叫super class。
61:03
啊,这个呢,你就这么一看就行,这些细节呢,所以怎么能掉呢,以后我们讲反射的时候会说哈,诶,你从名字上来看,就是获取当前这个类的负类吧。那这个打印的是谁?是不是就B了?哎,对啊,你看run一下。这不有B吗?呃,因为你这个方法里边定义的这个,呃类不类,它的负类呢,这不就我们是这个B类吗。啊,就这个道理。啊,这个大家体会体会,哎,其实呢,只要接口这块你会了,抽象类这块呢也类似。啊,都是你有,你就拿这个抽样类,或者拿这个接口去充当里边有抽样方法,你就重写一下就完了呗。体会一下啊好,这个是举例四,然后呢,再看能不能行啊,这个我们就彻底给大家呢,就。绕懵了啊,看你能不能蒙,不蒙了那就超脱了啊。我直接呢,在这个位置,我就扭一个B是吧。
62:01
然后直接呢,我就调这个MESSAGE1了,显然这个不靠谱啊,这是抽象类,你不能找对象,我在这个位置呢,是不是给你把这个方法就。重写一下呗,这个叫方法一吧。我再掉M1是不是掉的就是它。诶,先彻底懵了,然后我们再去清醒是吧,否定之否定啊。哎,这不就吊打他吗?能不能行啊,好,能行再来。这不都到头了吗?没到头呢啊拉一个C。C里边有个方法。哎,我叫method。嗯,二吧。那这个是一个普通的类了啊,所以这里边不就有这个方法体了吗?我就这样写了一下啊好,这个洗完以后呢,那么再回来。举例六是CC。然后你一个C。然后呢,C点掉MA2,这个没有任何问题。
63:00
这块也不应该有任何问题啊,好,这是最一般的情况了,呃,然后呢,接着我们来一个举例七啊。你看我咋写的啊,C一个C。嗯,叫C1了啊,然后你又一个C。诶,整个大括号。没了。然后C一点调的。诶,这也可以啊。哎,这个呢,哎,为什么加个大号呢。把它理解成我们相当于是提供了。一个继承于。对,继承于这个C的子类的对象了。但这个子类呢,是匿名的是吧。啊,因为呢,你这个C这个类里边也没有触法方法,所以他也没有提示我要去重启,我就彻底没重启。诶,那你这块调MA2,只不过打印的还是C而已嘛。对,你看直播打印的还是C而已,那如果这个C1跟上面一样啊,我这样c1.getclass打印是不是这个大家也能够猜出来啊。
64:10
是不是就成这样了?是吧,然后呢,我这时候呢再调啊c.get class.get super class这是谁呀。是不是就是C呀。哎,注意啊。你看这就是C,他跟我没有加大括号呢,区别很大,没加get class是不是就是C了。然后get class呢?对,那不就成object了吗?啊,有这样的这个场景,哎,所以加跟不加呢,你看这个区别还挺大的啊。啊,当然了,你说我这块呢,我也完全可以呢,那你自己呢,再去造一个,比如说叫C2,那无外乎就是这个位置呢,我们把这个方法给它重写了是吧。Method。二。哎,那重写这里边你就可以叫,比如说叫S一个C这个你再调哎MAC2的时候呢,诶这个C2啊,那你调的不就是你自己这个吗。
65:01
哎,这个呢还行啊,关键就是上面这个没有重启的时候呢,稍微的关注一下。那彻底呢,就说完了。啊,其实呢,虽然写的情况很多,但是其实呢,你一拢的话呢,无外乎就是提供所谓的不管是类也好,抽象类也好,接口也好,只是呢,体现了一个叫匿名的子类啊,或者叫实现类啊,哎,这个事儿其实呢,这写了这么多例子啊,它其实整个套路格式都是类似的。哎,大家稍微体会一下,以后的话呢,我们会去出现类似于这样的一些场景,到时候大家呢,诶,你知道是什么意思,自己呢,也可能会去写就OK了。好,那么至此呢,咱们关于这个内部类呢,就告一段落啊。
我来说两句