package(☆☆):就是文件夹,将字节码(.class)进行分类存放
包的写法(☆☆☆☆)
package 包名;
包的注意事项(☆)
A:package语句必须是程序的第一条可执行的代码
B:package语句在一个java文件中只能有一个
C:如果没有package,默认表示无包名
案例:在一个java文件里面
package com.heima;
class Demo1_Package {
public static void main(String[] args) {
}
}
//package com.heima; //报错: 因为 package语句必须是程序的第一条可执行的代码 所以package语句在一个java文件中只能有一个
//class Package {
//}
带包的类的编译和运行(☆):
编译:javac -d . Person_Test.java (javac -d . 类名.java)
比如:在D盘下有Person_Test.java ,在D盘下打开dos命令行 执行 javac -d . Person_Test.java 命令
就会生成一个D:/com/heima/Person_Test.class
运行:java com.heima.Person_Test ((当前路径下,不要跑到包里面去运行)java 类的全路径名)
比如:在D盘下打开dos命令行(当前路径下,不要跑到D:/com/heima去打开dos) 执行java com.heima.Person_Test
不同包下类之间的访问(☆)
1)类的全路径名 变量名 = new 类的全路径名();
案例:一个java文件里面是Demo1_Package类
package com.heima;
class Demo1_Package {
public static void main(String[] args) {
//Person p = new Person(); //报错:不同包下的类不能直接访问
com.baidu.Person p = new com.baidu.Person(); //类的全路径名
}
}
下面是另一个java文件里面是 Person类
package com.baidu;
class Person {
String name;
int age;
}
2)package和class之间 加入一个"import 包;"然后 ,就可以直接访问不同包下的类了
案例:一个java文件里面是Demo1_Package类
package com.heima;
import com.baidu.Person; //导包
class Demo1_Package {
public static void main(String[] args) {
Person p = new Person(); //导包后,就能直接访问了
}
}
另一个java文件里面是 Person类
package com.baidu;
class Person {
String name;
int age;
}
修饰符(☆☆)
权限修饰符的访问权限(☆☆☆☆)
本类 同一个包下(子类和无关类) 不同包下(子类) 不同包下(无关类)
private Y
默认 Y Y
protected Y Y Y
public Y Y Y Y
private: 是为本类准备的
默认:是为同一个包下的类准备的
protected:是为子类准备的 无论子类在任何地方
public: 为所有类准备的
各种修饰符都能修饰什么内容(☆)
类 成员变量 成员方法 构造方法
private √(修饰内部类) √ √ √(工具类)
默认 √ √ √ √
protected √(修饰内部类) √ √ √
public √ √ √ √
abstract √(抽象类) √
static √(修饰内部类) √ √
final √(不能被继承) √(常量) √(不能被重写)
每个内容一般都用什么修饰符修饰(☆):
类:public
成员变量:private
构造方法:public (当定义一个工具类的时候 可以用private)
成员方法:public
接口中的成员变量:public static final
接口中的成员方法:public abstract
内部类(☆☆):类内部的类就叫做内部类
访问特点(☆☆☆):
外部类访问内部类里面的内容 ,必须创建内部类的对象来访问
内部类访问外部类的内容, 直接访问 包括私有
代码:
class Demo1_InnerClass {
public static void main(String[] args) {
//Inner i = new Inner(); //报错,因为内部类是写在其他类的内部 不能这样直接创建内部类的对象
//i.method();
Outer.Inner oi = new Outer().new Inner(); //创建内部类对象 格式 :外部类名.内部类名 = 外部类对象.内部类对象
oi.method();
}
}
class Outer {
private int num = 10; //外部类的私有属性
class Inner {
String name = "内部类";
public void method() {
System.out.println(num); //内部类访问外部类的内容, 直接访问 包括私有
}
}
public void show(){
//System.out.println(name); //报错:外部类不能直接访问内部类的内容
Inner i = new Inner();
System.out.println(i.name); //这样才是正确的 外部类访问内部类里面的内容 ,必须创建内部类的对象来访问
}
}
成员私有内部类(☆):
class Demo2_InnerClass {
public static void main(String[] args) {
//Outer.Inner oi = new Outer().new Inner();//不能创建私有内部类的对象 因为内部类被私有了
//oi.method();
Outer o = new Outer();
o.print();
}
}
class Outer {
private int num = 10;
private class Inner { //内部类私有 是为了让内部的这个类更安全 比如:内部类就相当于人类的心脏 怎么能让外面直接访问你的心脏呢?
public void method() {
System.out.println(num);
}
}
public void print() {
Inner i = new Inner();
i.method();
}
}
成员静态内部类(☆)
class Demo1_InnerClass {
public static void main(String[] args) {
Outer.Inner oi = new Outer.Inner(); //外部类名.内部类名 对象名 = 外部类名.内部类对象;
oi.method();
Outer.Inner2.print(); //直接访问静态内部类里面的静态方法
}
}
class Outer {
static class Inner { //静态成员内部类
public void method() {
System.out.println("method");
}
}
static class Inner2 { //静态成员内部类
public static void print() { //静态方法
System.out.println("print");
}
}
}
内部类对象如何能访问当前外部类对象的成员变量?(☆)
class Test1_InnerClass {
public static void main(String[] args) {
Outer.Inner oi = new Outer().new Inner();
oi.show();
}
}
//要求:使用已知的变量,在控制台输出30,20,10。
class Outer {
public int num = 10;
class Inner {
public int num = 20;
public void show() {
int num = 30;
System.out.println(num); //访问的是局部变量 30
System.out.println(this.num); //访问的是成员变量 20
System.out.println(Outer.this.num);//外部类名.this 访问的是当前外部类对象的num 10 (请注意这里是"当前外部类对象" ,如果不明白什么是"当前外部类对象"请看下面的案例)
}
}
}
这样类型的题的变形
class Test1_InnerClass {
public static void main(String[] args) {
Outer ot = new Outer();
ot.num = ot.num - 5;
Outer.Inner oi = ot.new Inner();
oi.show();
}
}
class Outer {
public int num = 10;
class Inner {
public int num = 20;
public void show() {
int num = 30;
System.out.println(num); //访问的是局部变量 30
System.out.println(this.num); //访问的是成员变量 20
System.out.println(Outer.this.num); //外部类名.this 访问的是当前外部类对象的num 5(因为 当前外部类对象ot的num值已经改变成了5 ot.num = ot.num - 5;)
System.out.println(new Outer().num); //一个新的外部类对象的num 10
}
}
}
局部内部类 访问局部变量 ,局部变量前面必须加final修饰,为了延长局部变量的生命周期(☆☆☆☆☆)
class Demo1_InnerClass {
public static void main(String[] args) {
Outer o = new Outer();
o.method();
}
}
class Outer {
public void method() {
final int num = 10;
class Inner {
public void print() {
System.out.println(num);
}
}
Inner i = new Inner(); //对象的生命周期比局部变量长,
i.print(); //当method()方法执行完毕后,i还存在着 就会导致 如果i对象还想访问num ,而num已经消失了,访问不到了。所以在num前面加final 永远放到常量池里面去,常量池的东西 永远都不会消失(虚拟机挂掉才会消失)
}
/*public void run() {
Inner i = new Inner(); //局部内部类,只能在其所在的方法中访问
i.print();
}*/
}
以上代码的变形体如下(此代码和day15将要学习的迭代器的源码有些类似):
class Demo1_InnerClass {
public static void main(String[] args) {
Outer o = new Outer();
Iff i = o.method(); //用父类的引用来接收 method()方法的返回值
//method()方法执行完毕后 method()内部的num如果不加final的话 就消失了 那下面的i.print()就不能再使用num了,所以num前面必须加上final修饰
i.print(); //对象调方法
}
}
interface Iff
{
public abstract void print();
}
class Outer {
public Iff method() { //此方法 返回值 是一个Iff 接口,所以该方法必须要返回一个Iff的子类对象
final int num = 10;
class Inner implements Iff{
public void print() {
System.out.println(num);
}
}
Iff i = new Inner(); //父类引用指向子类对象
return i; //返回一个 Iff的子类对象
}
}
匿名内部类(☆☆):
前提:有一个接口或者抽象类 或者 普通的类
格式(☆☆☆☆☆):
new 接口名或者抽象类名(){
重写方法;
};
本质(☆☆☆☆☆):就是接口或者抽象类或者普通类的一个子类对象
|
|