- 包:
- 包的概述:其实就是文件夹
- 包的作用:对类进行分类管理
-
包的划分:按照模块和功能分
学生的增加,删除,修改,查询
老师的增加,删除,修改,查询
以及以后可能出现的其他的类的增加,删除,修改,查询
-
- 定义包的格式:package 包名;
多级包用.分开即可
表示当前代码文件的相对目录
- 定义包的格式:package 包名;
相对路径:com.shujia.java.day13.BaoDemo
绝对路径:D:\IdeaProjects\bigdata13\src\com\shujia\java\day13\BaoDemo.java
-
- 注意事项:
package语句必须是程序的第一条可执行的代码
package语句在一个java文件中只能有一个
如果没有package,默认表示无包名
- 带包的类的编译和运行
- 导包:
package com.shujia.java.day13.demo2; //import com.shujia.java.day13.demo1.Demo; //import com.shujia.java.day13.demo1.Demo2; //* 的作用代表的是将该目录下所有的文件导入进来,我推荐当导包的个数大于28个的时候用* //Scala里面是 _ //import com.shujia.java.day13.demo1.*; public class Test { public static void main(String[] args) { // Demo d = new Demo(); // d.sum(1,2); // Demo2 demo2 = new Demo2(); // demo2.sub(3,2); //如果不适用import导包 //那么在每次使用其他包内容的时候,需要将完整路径写出来 com.shujia.java.day13.demo1.Demo d = new com.shujia.java.day13.demo1.Demo(); d.sum(2,2); } } package com.shujia.java.day13.demo1; public class Demo2 { public void sub(int a,int b){ System.out.println("a-b= "+(a-b)); } } package com.shujia.java.day13.demo1; public class Demo { public void sum(int a,int b){ System.out.println("a+b= "+(a+b)); } }
-
- 链式编程:
/* 链式编程: 1、对象1.对象2.对象3..方法() 2、对象1.方法1().方法2()...方法n() */ interface PlayGame2{ public abstract void playLol(); } class PlayGameDemo2{ public PlayGame2 fun(){ PlayGame2 pg2 = new Student6(); return pg2; } } class Student6 implements PlayGame2{ @Override public void playLol() { System.out.println("学生打英雄联盟"); } } public class ChainDemo { public static void main(String[] args) { PlayGameDemo2 playGameDemo2 = new PlayGameDemo2(); PlayGame2 pg2 = playGameDemo2.fun(); pg2.playLol(); System.out.println("==========用链式编程改进==========="); //每次调用完毕方法之后,返回的是一个对象 //因为对象才能去调用方法 playGameDemo2.fun().playLol(); } }
- 类及其成员的修饰符
修饰符:
权限修饰符:public,protected,默认的,private
状态修饰符:static,final
抽象修饰符:abstract
最常用的是public和private
类:
权限修饰符:默认的,public,
状态修饰符:final
抽象修饰符:abstract
最常用的是:public,默认的
成员变量:
权限修饰符:默认的,public,protected,private
状态修饰符:static,final(需要初始化值)
最常用的是:private
构造方法:
权限修饰符:默认的,public,protected,private
最常用的是:public
成员方法:
权限修饰符:public,默认的,protected,private
状态修饰符:static,final
抽象修饰符:abstract
最常用的是:public
常见的一些组合:
成员变量:public static final 在接口中遇见
成员方法:
1、public abstract
2、public static
3、public final
-
内部类:
- 把类定义在其他类的内部,这个类就被称为内部类
举例:在类A中定义一个类B,类B就被成为内部类
-
- 内部类的访问特点:
1、内部类可以直接访问外部类的成员,包括私有。
2、外部类要访问内部类的成员,必须创建对象。
class Outer { private int num = 20; class Inner { int num = 200; int num1=2000; public void show() { System.out.println(num);//200 } } public void show2(){ Inner inner = new Inner(); System.out.println(inner.num);//200 相当于this.num; inner.show(); System.out.println(num);//20 // System.out.println(num1);//错误写法 } } public class InnerClassDemo1 { public static void main(String[] args) { Outer outer = new Outer(); outer.show2(); } }
按照内部类在类中定义的位置不同,可以分为如下两种格式:
成员位置(成员内部类)
局部位置(局部内部类)
class Outer2{ //定义在成员位置,叫做成员内部类 class Inner{ } public void show(){ //定义在局部位置,叫做局部内部类 class Inner2{ } } }
成员内部类:
1、内部类可以访问外部类的成员,包括私有
2、正确的创建内部类的对象格式:
外部类名.内部类名 对象名 = 外部类对象.内部类对象;
class Outer3{ private int num = 20; //成员内部类 class Inner3{ public void show(){ System.out.println(num); } } } public class InnerClassDemo3 { public static void main(String[] args) { //要想访问内部类的成员,就必须要创建内部类的对象 //但是按照我们原先创建对象的方式,找不到类,创建不了对象 // Inner3 inner3 = new Inner3(); // inner3.show(); //正确的创建内部类的对象格式: //外部类名.内部类名 对象名 = 外部类对象.内部类对象; Outer3.Inner3 oi = new Outer3().new Inner3(); oi.show(); } }
成员内部类常用两种修饰符
/* 成员内部的常见修饰符 private 为了保证数据的安全性 static 为了让数据访问更方便 有一个人(人有身体,身体里面有心脏) */ class Body{ public static class Heart{ public static void bloodXunHuan(){ System.out.println("提供血液循环"); } } } public class InnerClassDemo2 { public static void main(String[] args) { //外部类名.内部类名 对象名 = 外部类对象.内部类对象; // Body.Heart bh = new Body().new Heart(); //内部类加入了private权限修饰符之后,就不能被访问了 //当内部类被静态修饰后,访问的格式就变了: //外部类名.内部类名 对象名 = new 外部类名.内部类名 Body.Heart bh = new Body.Heart(); bh.bloodXunHuan(); //调用bloodXunHuan()另一种方式 链式编程 // new Body.Heart().bloodXunHuan(); Body.Heart.bloodXunHuan(); } }
小例题
/* 在控制分别输出:30,20,10 class Outer { public int num = 10; class Inner { public int num = 20; public void show() { int num = 30; System.out.println(?); System.out.println(??); System.out.println(???); } } } 注意:内部类与外部类没有继承关系 */ class Outer4 { public int num = 10; class Inner { public int num = 20; public void show() { int num = 30; System.out.println(num); System.out.println(this.num); //第一种方式,创建外部类对象,访问成员变量 System.out.println(new Outer4().num); //第二种方式 System.out.println(Outer4.this.num); } } public void show(){ System.out.println(this.num); } } public class InnerClassDemo5 { public static void main(String[] args) { Outer4.Inner oi = new Outer4().new Inner(); oi.show(); } }
- 局部内部类:
1、可以直接访问外部类的成员
2、可以创建内部类对象,通过对象调用内部类方法,来使用局部内部类功能
class Outer5{ private int num = 10; public void show(){ int num2 = 100; class Inner{ int num3 = 200; public void show2(){ // num2 = 400; //jdk1.8之后会自动在局部方法上的局部变量添加final System.out.println(num3); } } num2 = 500; System.out.println(num2);//500 Inner inner = new Inner(); inner.show2(); } // Inner i = new Inner(); } public class InnerClassDemo4 { public static void main(String[] args) { Outer5 outer5 = new Outer5(); outer5.show(); } }
-
匿名内部类:就是内部类的简化写法。
- 前提:存在一个类或者接口
这里的类可以是具体类也可以是抽象类。
-
- 格式:new 抽象类名或者接口名() {
重写方法;
}
-
- 本质:是一个继承了类或者实现了接口的子类匿名对象
注意事项:
interface Inter{ public abstract void show(); public abstract void show2(); } abstract class Demo7{ public abstract void function1(); } class Outer7{ public void fun(){ // InterImpl inter = new InterImpl(); // inter.show(); // inter.show2(); //匿名内部类,匿名对象 new Inter(){ @Override public void show() { System.out.println("show"); } @Override public void show2() { System.out.println("show2"); } }.show(); new Inter(){ @Override public void show() { System.out.println("show"); } @Override public void show2() { System.out.println("show2"); } }.show2(); //问题:如果我这个接口有很多方法,还要使用匿名内部类的形式就很麻烦 //因为每次调用里面实现的方法,多需要创建一个内部类 //怎么改进? System.out.println("====改进版======="); Inter i = new Inter(){ //多态 @Override public void show() { System.out.println("show"); } @Override public void show2() { System.out.println("show2"); } }; i.show(); i.show2(); System.out.println("============"); DemoTest demoTest = new DemoTest(); demoTest.function1(); new Demo7(){ @Override public void function1() { System.out.println("function1"); } }; } } class InterImpl implements Inter{ @Override public void show() { System.out.println("show"); } @Override public void show2() { System.out.println("show2"); } } class DemoTest extends Demo7{ @Override public void function1() { System.out.println("function1"); } } public class InnerClassDemo7 { public static void main(String[] args) { Outer7 outer7 = new Outer7(); outer7.fun(); } }
匿名内部类在开发中的使用:接口作为参数传递。实际上传递的时接口实现类对象
interface Person8{ public abstract void study(); } class PersonDemo8{ //当接口做为参数传递的时候,实际上需要的是该接口实现类的对象 public void fun(Person8 person8){ person8.study(); } } class Student8 implements Person8{ @Override public void study() { System.out.println("学生学习"); } } public class InnerClassDemo8 { public static void main(String[] args) { PersonDemo8 personDemo8 = new PersonDemo8(); Student8 student8 = new Student8(); personDemo8.fun(student8); System.out.println("使用匿名内部类实现====="); personDemo8.fun(new Person8(){ @Override public void study() { System.out.println("这是使用匿名内部类的方式实现"); } }); } }
小练习:
/* interface Inter { void show(); } class Outer { //补齐代码 } class OuterDemo { public static void main(String[] args) { Outer.method().show(); } } 要求在控制台输出”HelloWorld” */ interface Inter9 { public abstract void show(); } class Outer9 { //通过观察main方法的实现发现,可以直接通过类名.方法的形式 //说明method方法是静态的 //又因为调用完method方法之后还可以调用方法,说明method方法的返回值是一个对象 //又因为,后面调的方法是show()方法,通过观察发现,是接口Inter9中的show()方法 //所以大胆判断,method方法的返回值是接口Inter9 public static Inter9 method(){ //由于返回值类型是一个接口类型,所以需要的是该接口实现类的对象 //在还没有学习匿名内部类之前的做法 // Demo9 demo9 = new Demo9(); // return demo9; //学习匿名内部类之后 return new Inter9(){ @Override public void show() { System.out.println("HelloWorld"); } }; } } class Demo9 implements Inter9{ @Override public void show() { System.out.println("HelloWorld"); } } class InnerClassDemo9 { public static void main(String[] args) { Outer9.method().show(); } }