javaSE笔记1

字符编码
1、Java 的字符类型(char)采用的是Unicode 编码方案,每个Unicode 码为两个字节,占用16个比特位,这是较老的版本。现在unicode编码占几位,取决于实现unicode的用的什么编码,utf-8、utf-16、utf-32规定了用多少位表示。UTF-8 是目前互联网上使用最广泛的一种 Unicode 编码方式,它的最大特点就是可变长。它可以使用 1 - 4 个字节表示一个字符。
2、Java源文件的编码格式是自己在编写Java源文件的时候指定的。
   javac编译器读取Java源文件的默认编码是操作系统的编码(windows中文版的默认编码是GBK),但是可以通过-encoding参数指定编码。
   javac编译器生成的字节码文件的编码是UTF-8。

类型转换
1、int类型的变量或字面量占四个字节,long类型占8个字节。将long类型强制类型转换成int类型的话,底层是将long类型的高四个字节砍掉。
2、当一个整数字面值(一定是字面量,不能是变量)没有超出byte、short、char类型的取值范围的时候,这个整型字面量可以直接赋值给byte、short、char类型的变量。
3、再任何任何时候编译器看到整数的时候,都把他当作int类型来处理的。
4、byte、short、char类型的变量做混合运算的时候,实际上是变量中保存的值在做运算,变量中保存的值是整形字面量,所以首先会各自转换成int类型在做运算。
5、当不同的类型变量做混合运算的时候,首先会把各自转换成最大的容量在进行运算。
6、多种数据类型(包括字面量和变量)混合运算,各自先转换成容量最大的那一种再做运算;
7、再java中只要是整形字面量(或者是整形字面量的运算),编译器都会把整形字面量(或者整型字面量的运算结果)看作是int类型的数据。
   代码
    //再java中只要是整形字面量或者是多个整形字面量的运算,编译器都会把整形字面量或者多个整型字面量的运算结果看作是int类型的数据。
    int i1 = 2147483647 + 1;//等号后面两个int类型的字面量的运算,运算结果仍为int类型,类似“((int)(2147483647 + 1))”,因为默认就是int类型强转不需要我们自己写,编译器自动完成
    int i2 = 1 + 1;//等号后面两个int类型的字面量的运算,运算结果仍为int类型,类似“((int)(1 + 1))”,因为默认就是int类型强转不需要我们自己写,编译器自动完成
    long l1 = 2147483647;l1++;//l1是2147483648;等价于l1 = l1 + 1.
    long l2 = 2147483647 + 1;//l2是-2147483648;等价于l2 = (int)(2147483647 + 1).
8、使用++或者扩展赋值运算符(+=、-=、...)永远都不会改变运算结果的类型。(所以这些运算符可能会损失精度)
   代码
    byte b = 1;
    b++;//等价于b = (byte) (b + 1);而不是b = b + 1 结果为-128
    b+=1;//等价于b = (byte) (b + 1);而不是b = b + 1 结果为-127
    int i = 10;i++;//等价于 i = i + 1;i + 1 相当于(int)(i + 1)因为运算结果本类就是int;类型的所以不用手动加强制类型转换符

运算符
1.逻辑运算符:要求两边的算子都是布尔类型,并且逻辑运算符最终的运算结果也是一个布尔类型。
    & 逻辑与
    | 逻辑或
    !逻辑非(取反)
    ^ 逻辑异或
    && 短路与
    || 短路或
2.位运算符:要求两边的算子都是整形的字面量
    & 按位与
    | 按位或
    ~ 按位取反
    ^ 按位异或
    << 左移(包括有符号和无符号)
    >> 有符号数右移(高位补符号位)
    >>> 无符号数右移(高位补0)

控制语句
1、对于if语句来说,在任何情况下只能有1个分支执行。(if语句只要有一个分支执行了,整个if语句就结束了)
2、switch后面的小括号中的数据类型只能是int(或者是byte、short、char)或String类型的,还可以是枚举类型。
    switch后面的小括号中必须是“枚举类型名.枚举类型值”
    case后面的匹配项必须是“枚举类型值”【不能有枚举类型名】
    默认case后面的匹配的“数据的类型的值”就是switch后面的小括号中的数据的类型,不然编译报错
3、if后面的小括号中可以是一个赋值运算符,赋的必须是布尔类型的值。
4、break转向语句可以出现在switch语句中和循环语句中。【break出现在switch中防止case穿透现象,break出现在循环语句中用于终止离他最近的那个循环的执行。】
   break还可以出现在代码块中:
   代码块名字: {
       代码块体;
       break 代码块名字;//用于结束代码块的执行
   }
5、如果想让break和contiune操作的不是距离它最近的那个循环可以给循环起名字。【代码如下】
   代码
    a:for (int i = 0; i < 10; i++) {
        b:for (int j = 0; j < 10; j++) {
            if (j == 5)
                break a;//break只能结束包裹它的循环,不能写”break c;“
        }
    }
    c:for (int i = 0; i < 10; i++) {

    }
    switch也是一样的原理,也可以给switch起名字,用“break 名字;”的语法结束指定的switch语句。
    
方法
1、方法声明的语法结构:
    [修饰符列表] 返回值类型 方法名(形式参数列表) {
        方法体;
    }
2、静态方法中:当主调方法和被调方法在同一个类中的时候,在调用方法的时候“类名.”可以省略不写。
3、方法体当中的代码是“自上而下,逐行执行”!上一行代码不结束,下一行代码永远不可能执行到。
4、JVM中三块主要的内存空间:栈内存、堆内存、方法区内存。
    栈内存又叫:动态区内存,在方法被调用的时候,该方法需要的内存空间在栈中分配。
    方法区内存又叫:静态区内存,(虽然名字带有“方法”二字实际上跟方法没有关系),存放的是代码片段的,比如一个class在被加载到JVM当中的时候方法区内存中存放的是“.class文件”的所有相关数据信息。
    堆内存:凡是通过“new”运算符创建的对象都存储在堆内存当中。
5、方法重载(overload):在同一个类中、方法名相同、参数列表不同(个数不同、类型不同、顺序不同)。
6、方法重载只与方法名和形参列表有关系(和其他都没有关系)。
7、递归调用是自己调用自己,被调方法和主调方法肯定都是在同一个类中,所以调用方法(自身)的时候“引用.”或者“类名.”都可以省略不写。
8、递归必须有结束条件,否则必定会发生“StackOverflowError”栈内存溢出错误。

面向对象
1、类=属性(状态特征)+方法(行为动作特征)
2、类->对象(实例化) 、 对象->类(抽象)
3、定义类的语法格式:
    [修饰符列表] class 类名 {
        类体 = 属性 + 方法;
        //因为对象的属性都是以数据的形式存在的,数据必须找一个东西存起来,这个东西就是变量(所以属性经常以变量的形式存在)
    }
4、在方法体内定义的变量叫做局部变量,在方法体之外类体之内定义的变量叫成员变量。
5、保存了对象内存地址的变量叫做引用。
6、访问类成员:类成员包括:成员变量和成员方法。(成员变量包括静态变量和实例变量、成员方法包括静态方法和实例方法)
   访问实例成员:
   访问实例变量的语法结构:“引用.实例变量名”。
   访问实例方法的语法结构:“引用.实例方法名(实参列表)”。
   访问静态成员:
   访问静态成员变量:“类名.静态成员变量名”或者“引用.静态成员变量名”
   访问静态成员方法:“类名.静态成员方法名(实参列表)”或者“引用.静态成员方法名(实参列表)”
   但是静态成员不建议使用“引用.”的方式访问。
8、对象:在堆内存中“new”出来的。
   引用:保存了某个对象的内存地址的变量。
9、java中垃圾回收机制主要针对的是“堆内存”。
   没有任何引用指向该对象的时候,该对象会被垃圾回收器回收。
10、“空引用”访问实例相关的数据时,都会出现“空指针异常”(NullPointerException)。
11、变量赋值或变量作为实参调用函数的时候:不管是基本数据类型还是引用数据类型,统一都是将变量中保存的那个“值”复制一份,传递下去。

构造方法
1、当一个类没有提供任何构造方法,系统会默认提供一个无参的构造方法。(这个无参数的构造方法叫做“缺省构造器”)
   当一个类中手动提供了构造方法,那么系统将不在提供无参构造方法。
2、构造方法语法结构:
    [修饰符列表] 构造方法名 (形式参数列表) {
        构造方法体;
    }
3、构造方法都是通过“new”运算符来调用的。
4、构造方法可以重载。
5、实例变量是在构造方法执行的过程中完成初始化的,完成赋默认值的。
6、对于实例变量来说,只要没有在构造方法中手动赋值,系统统一给我们赋默认值。
7、构造方法的作用:完成对象的创建,初始化实例变量。

封装
1、实现步骤
    1.1属性私有化。
    1.2对外提供set和get方法。(实例方法不能带static)
2、封装的作用
    保证内部结构的安全。
    屏蔽复杂,暴露简单。
    
static关键字
1、static修饰的都是类级别的。
2、变量的分类
    局部变量:在方法内部定义的变量,局部变量不能加static。
    成员变量:在方法体之外声明的变量。
        实例变量:用“引用.”的方式访问。
        静态变量:用“类名.”的方式访问。
3、方法的分类
    静态方法:修饰符列表中含有static关键字的方法(使用“类名.”的方式调用)。
    实例方法:修饰符列表中没有static关键字的方法(使用“引用.”的方式调用)。
4、如果在同一个类中,实例方法可以直接省略“类名.”调用静态方法(系统会自动添加“当前类名.”),但是静态方法不可以直接省略“引用.”调用实例方法。
5、java的任何方法中都不可以声明静态变量(包括静态方法、实例方法、构造方法)?
    在方法内部定义的叫“局部变量”,而不是静态变量,局部变量不能加static,包括protected, private, public这些也不能加。静态变量是定义在类中,方法体外面的。
    局部变量是保存在栈中的,而静态变量保存于方法区,局部变量出了方法就被栈回收了,而静态变量不会,所以在局部变量前不能加static关键字。
    由于JAVA规定,方法内定义的都是局部临时变量,且由于内存分配,会创建一个栈帧保存局部变量表、操作数栈,动态链栈等,在方法结束后,栈帧会出栈并释放掉所有局部变量。这个时候定义一个静态变量那会不会造成内存泄漏呢?会的,由于静态变量生命周期同类的对象一致。因此不能。
    在人性化的设计中,静态变量大都用来供外界访问或类中各个方法共享。你在一个方法中定义了一个静态变量,那对于其他方法来说,前者内部是不可见的。且对于外界来说同样也是不可见的。这样便毫无意义。
6、调用“静态变量”和“静态方法”的时候不需要对象的参与,所以没有空指针异常(用空引用去调用也不会有空指针异常)。
7、只要是方法,不管是静态方法、实例方法、构造方法他们在运行的时候都是需要压栈。
8、局部变量在栈中存储、实例变量在堆内存中存储、静态变量在方法区内存中存储。
9、静态变量在类加载时初始化(系统给他赋默认值,但是静态变量一般会手动赋一个默认值),不需要new对象静态变量的空间就开辟出来了,静态变量存储在方法区中。
10、如果某个类型的所有对象的某个属性值都是一样的该属性定义为静态的。
    如果某个类型的所有对象的某个属性值都不一样该属性定义为实例变量。
11、用static关键字可以定义:静态代码块。
    语法结构:  static {
                    Java语句;
                    ....
                }
12、静态代码块在类加载的时候执行,并且只执行一次(根据代码块在类中出现的“先后顺序”依次执行)。
13、类加载完了之后才开始压栈执行方法,所以main方法是在静态代码块执行之后才执行的。
14、静态代码块是一个非常特殊的代码块,编译器会将同一个类中所有的静态代码块合并成一个static{},它们共享一次压栈弹栈操作。
15、静态代码块中可以使用静态变量。
16、实例初始化代码块里面的代码会被自动添加到「所有的构造器」的开头,代码块本身无额外压栈弹栈操作。而且要注意的是,这里说的是「所有的构造器」,有几个构造器,汇编代码中就会出现多少的冗余片段。如果有很多构造器,那就会有相当的浪费。
17、作为某个类的内部类时,才能用static修饰。主类不能用static修饰。

this关键字
1、this是一个变量、是一个引用。
2、this存储在堆内存对象的内部。this代表的就是“当前对象”。
3、this只能使用在实例方法中,不能使用在静态方法中。
4、this区分局部变量和实例变量的时候不能省略“this.”。
5、“this(实参列表);”可以通过一个构造方法去调用另一个构造方法。
   “this(实参列表);”只能在构造方法法中,普通方法中不能使用。
   “this(实参列表);”只能用在构造方法的第一行,并且只能使用一次。

继承
1、基本作用:子类继承父类,代码可以得到复用。
   重要作用:因为有了继承才有了后面的“方法覆盖”和“多态”机制。
2、语法结构: 
    [修饰符列表] class 类名 extends 父类名 {
        类体 = 属性 + 方法;
    }
3、java中只支持单继承,不支持多继承,但是可以间接继承产生多继承的效果。
4、除了构造方法其他都可以被继承,但是私有的成员无法再子类中直接访问(私有的成员只能在父类中通过父类的“引用”或“类名.”去访问)。
5、父类:基类、超累、superclass
   子类:派生类、扩展类、subclass
6、子类继承父类,“子类引用.”或者“子类类名.”可以访问父类中非私有的数据(包括“成员变量”和“成员方法”)。
7、子类继承父类除构造方法之外的所有数据,只不过私有数据不能在子类中直接访问。
8、引用“点”的时候只能“点”出来本类或者本类的父类中的可见的属性或方法。
9、Java中规定没有显示继承任何类,默认继承java.lang.Object类,一个类与生俱来就有Object类中的所有特征。
10、找属性是从编译类型开始往父类的方向寻找,找方法是从运行类型开始往父类的方向寻找。
    找属性从编译类型开始寻找:一但找到了就立马停止继续寻找:如果可以访问那么返回属性值,如果不可以访问那么“编译报错”。
    如果通过子类对象的引用调用方法,从当前类开始向父类的方向寻找,在哪个父类找到该方法的时候,在方法执行过程中,子类对象的编译类型已经隐式类型转换成哪个父类对象的引用.
11、凡是采用“is a”能描述的,都可以继承。(例如“Cat is a Animal”).
12、当直接输出一个“引用”的时候,println()方法会先自动调用“引用.toString()”,然后输出toString()方法的执行结果。
13、类加载的时候,有继承关系的父子类,JVM先加载父类再去加载子类。
14、在本类方法当中this,一定是本类的对象的引用。

方法覆盖(override)
1、什么时候需要方法覆盖?
    当子类从父类中继承过来的方法已经无法满足子类的业务需求的时候, 子类有必要将该方法重新编写。
2、方法覆盖:又叫方法重写,英语单词叫做:override、overwrite.
   与方法重载区分开:方法重载(overload):在同一个类中方法名相同、参数列表不同。
3、满足什么条件构成方法覆盖?
    条件一:两个类必须要有继承关系。
    条件二:子类方法的形参列表、方法名称,要和父类方法的形参列表,方法名称完全一致。
    条件三:子类方法不能缩小父类方法的访问权限,但是可以扩大。
    条件四:子类方法的返回值类型和父类方法的返回值类型一样,或者是父类返回值类型的子类【对于返回值类型是基本数据类型来说,必须一致】。
    条件五:重写之后的方法不能比之前的方法抛出更多的异常,可以更少(针对的是编译时异常,运行时异常可以随便整)。但可以抛出父类方法异常的子异常。【父类不抛出异常,但是子类可以抛出运行时异常】
4、方法覆盖就是把继承过来的那个方法给覆盖掉了,继承过来的那个方法没了。
   当子类对父类继承过来的方法进行方法覆盖之后,子类对象调用该方法的时候,一定执行覆盖之后的方法。
   私有方法在子类中不可见,所以不能覆盖(想盖也盖不住啊)。【比如在父子类中各有一个私有的方法,那么子类这个方法不可能覆盖父类的方法,没有覆盖关系】
   构造方法不能继承,所以不能覆盖。
   静态方法不存在覆盖(静态方法覆盖没有意义)【静态方法是通过“类名.”的方式调用的,和底层new的那个对象没有关系,方法覆盖只针对实例方法】。
   覆盖只针对方法,不针对属性(父子类中的同名属性叫做“属性的隐藏”)。
5、方法覆盖和多态机制联合起来使用才有意义.  

多态
1、向上转型:Java中允许父类型的引用指向子类型的对象。(Animal a = new Cat();Cat is a Animal 可以说通)
2、无论是向上转型还是向下转型两种类型之间必须有继承关系,没有继承关系编译器报错。
3、“点”的时候只能“点”出来“编译类型”或者“编译类型的父类型”的属性或方法。
4、静态绑定成功之后才可以到达运行阶段。
5、因为有“编译阶段”和“运行阶段”呈现多种形态所以叫做“多态”。
6、向下转型:父 -> 子,当需要访问的是子类对象中特有的方法,此时必须进行向下转型。
7、instanceof运算符
    可以在运行阶段动态判断引用指向的对象的类型。
    语法结构:
        (引用 instanceof 类型)【引用所属的类型和后面的类型之间必须有继承关系,没有继承关系编译器报错。但是后面的可以是接口,接口可以与引用没有继承关系也不会编译报错】。
    运算结果是布尔类型的:true/false.
    假设(cat instanceof Animal)为true表示:cat指向的对象是Animal类型的对象或者是Animal类型的子类型的对象.    
8、多态在开发中的作用:降低程序的耦合度,提高程序的扩展力.
9、无论是向上转型还是向下转型,转换的都只是引用的类型,不可能转换对象的类型。【对象从new出来就在堆里面存放着,不可能改变对象的类型】。
10、多态:“确定”运行哪个方法是从编译类型开始往上寻找,实例运行的时候是从运行类型开始往上寻找。

super
1、super和this对比学习:
   this
    this能出现在实例方法和构造方法中,不能使用在静态方法中。
    this的语法是:“this.” 或者 “this()”。
    this.大部分情况下是可以省略的。
    this.区分实例变量和局部变量的时候不能省略。
    this()只能出现在构造方法的第一行,通过当前构造方法去调用“本类”中其他的构造方法,目的是:代码复用。
   super
    super能出现在实例方法和构造方法中,不能使用在静态方法中。
    super的语法是:“super.”、“super()”.
    super大部分情况下可以省略。
    super什么时候不能省略?如果父子类中有同名属性或方法,想在子类中访问父类中与子类中同名的属性或方法“super.”不能省略。
    super()只能出现在构造方法的第一行,通过当前的构造方法去调用“父类”中的构造方法,目的是:创建子类对象的时候,先初始化父类型的特征。
2、“this()”和“super()”只能使用一个。
3、当一个构造方法的第一行既没有“this()”又没有“super()”,默认会有一个super().表示通过当前的构造方法去调用父类的无参构造器,所以必须保证父类的无参构造方法是存在的。
4、Java语言中不管是new什么对象,最后老祖宗的Object类的无参数构造方法一定会执行。
5、super代表当前对象的父类型特征。
6、在实例化对象的时候一连串的调用构造方法,但是对象只创建了一个。
7、super不是引用,super也不保存内存地址,super也不指向任何对象。super只是代表当前对象内部的那一块父类型的特征。
8、System.exit(0);//用于退出java虚拟机。

final
1、final表示最终的,不可变的。
2、final可以修饰变量、方法、类。
3、final修饰的变量只能赋一次值。
    final修饰的成员变量不能有setter方法,只能有getter方法。
    final修饰的成员变量只能在构造方法中赋值(在构造方法中赋值就不能声明的时候赋值),或者在声明的时候直接给一个默认值(给默认值之后,就不能在构造方法中二次赋值了,二者只能在一处赋值)。
4、final修饰的方法无法被覆盖。
5、final修饰的类无法被继承。
6、final类无法被继承,没有继承关系就不存在方法覆盖,所以final类中的方法也无法被覆盖,所以final类中的方法定义为final的也就没有任何意义了。
7、使用final修饰的实例变量系统不会为它赋默认值,需要手动赋值。
8、final修饰的引用,一旦指向某个对象之后,就不能在指向其他对象,那么被指向的对象也就无法被垃圾回收器回收。
    final修饰的引用虽然指向某个对象之后就不能在指向其他对象了,但是所指向的对象内部的内存是可以被修改的。
9、final修饰的实例变量要不再“所有”构造方法中赋值,要不在声明的时候直接赋值(两处必须在一处赋完值)。
10、常量:static final联合修饰的变量称为“常量”。常量名全部大写,多个单词之间用下划线衔接。
11、常量一般都是公开的(public),因为公开别的类也不能修改,比较安全。并且不用封装。
12、final关键字意味着无法更改某些内容。static关键字意味着类级别的范围。当你在 Java 中组合 static final 时,你创建了一个对类来说是全局的且无法更改的变量。其他平台的开发人员会认为这种创建等同于全局常量变量。
13、final修饰的实例变量在构造方法中赋值的时候本类的每个对象该属性值可以不相同,但是对于static修饰的属于类和级别的,本类所有对象的该属性值都一样,static修饰的属性再加上final修饰的就属于类级别的且无法修改的全局常量。
14、final修饰的实例变量一般和static联合使用称为常量。
15、父类或者父类中的方法没有final修饰,子类继承后可以添加final修饰。

抽象类
1、对象往上抽就是类,类往上抽就是抽象类,抽象类往上抽就是接口。
2、类和类之间有共同特征,将这些具有共同特征的类再进一步抽象形成了抽象类。由于类本身是不存在的,所以抽象类无法创建对象。
3、抽象类属于引用数据类型。
4、定义抽象类语法结构:
    [修饰符列表] abstract class 类名 {
        类体;
    }
5、抽象类是用来被子类继承的。
6、abstract不能和final联合使用(抽象类就是被继承的,final修饰的类是无法被继承的,所以两者不能联合使用)。
7、抽象类的子类还可以是抽象类。
8、抽象类虽然无法实例化,但是抽象类有构造方法,这个构造方法是提供给子类使用的,因为子类的构造方法的第一行是“super()”。
9、抽象方法:没有实现的方法,没有方法体的方法。
    没有方法体,以分号结尾。
    前面修饰符列表中有abstract关键字。
    语法结构:  [修饰符列表] abstract 返回值类型 方法名(形式参数列表);
10、抽象类中不一定有抽象方法,抽象方法必须出现在抽象类中。
11、abstract与static不能同时使用,static关键字修饰的成员是属于类的,而abstract一般是用来修饰普通方法目的是为了让子类继承后重写该方法,而static修饰的方法是不存在继承重写的。
12、抽象类中可以有普通方法,但是普通类中不能有抽象方法。
13、一个非抽象的类继承抽象类,必须将抽象类中的所欲抽象方法实现(覆盖/重写)了(去掉方法修饰符列表中的abstract,添加上方法体)。
14、父类本来不是抽象类,继承之后可以变成抽象类;方法也可以,本来不是抽象方法,覆盖之后变成了抽象方法。
15、一个类继承抽象类之后,如果本类还是抽象类那么就可以不实现抽象类中的抽象方法。
16、抽象类中可以包含非抽象方法,但如果一个类中的所有方法都是非抽象方法,那这个类抽象没有任何意义。
17、普通类也可以继承父类,也可以把通用的方法放到父类,实现代码复用,为什么还要用抽象类?
    答:当父类的某些方法需要声明,但又不知如何实现时,可以将其声明为抽象方法,那么这个类就是抽象类。
18、abstract只能修饰“类”和“方法”,不能修饰属性和其他的。
19、抽象类本质还是一个类,它可以有任意成员,比如:非抽象方法、构造器、静态属性、静态方法等等。
20、抽象方法不能使用private、final和static来修饰,因为这些关键字都是和重写相违背的。
21、虽然抽象类不能new对象,但是可以使用匿名内部类的形式:
    new 抽象类名() {
        类体;
        //因为匿名内部类不是抽象类须实现抽象类中的所有抽象方法。
        //这里的抽象类名也可以时普通类名,也可以是接口名
        //这样弄出来的匿名内部类就相当于匿名内部类继承了普通类、或者抽象类、或者实现了接口的一个匿名内部类。
    };
     
接口基础语法
1、接口也是一种引用数据类型。[接口的父类也是Object类,只是不能显示的写出来]。
2、接口是完全抽象的。(抽象类是半抽象的)。
   抽象类中有构造方法,接口中没有构造方法。
3、接口怎么定义,语法是什么?
    [修饰符列表] interface 接口名 {
        接口体;
    }
4、接口编译之后也是一个“class”字节码文件。
5、接口支持多继承,一个接口可以继承多个接口(接口不能继承其他类)【但是抽象类可以继承普通类】。
    [修饰符列表] interface 接口名 extends 父接口名1,父接口名2... {}
    接口只能被接口继承,不能被类继承;
    接口只能被“普通类”或者“抽象类”实现,不能被接口实现;
    抽象类和普通类都分别只能被“普通类”或者“抽象类”继承,不能被接口继承,也不存在实现的概念;
6、接口中只有“常量”和“抽象方法”。
7、接口中所有的元素都是公开的(public)修饰的【实现接口中的方法,实现之后只能是公开的(public)】。
8、既然接口中的方法都是公开的抽象的(接口中的方法不能有方法体),所以接口中定义抽象方法时:public abstract修饰符可以省略。
9、接口中定义的变量都是常量:默认是“public static final”修饰,可以省略(接口中随便写一个变量就是常量【比如int a = 1;相当于public static final int a = 1;(必须初始化)】,可以直接用“接口名.”的方式访问)。
   接口中定义的方法都是抽象方法:默认是“public abstract”修饰,可以省略。
10、“类和类”、“类与抽象类”、“接口与接口”之间都叫做“继承”,类和接口之间叫做“实现”。
11、实现的语法结构: class 类名 implements 接口名1,接口名2,接口名3... {类体;}。
12、接口支持“多继承”和“多实现”(一个类可以实现多个接口)。
13、当一个非抽象的类,实现接口的话,必须将接口中的所有的抽象方法全部实现(覆盖、重写)。
14、接口和接口之间在进行强制类型转换的时候,没有继承关系,也可以强转,但是在运行的时候可能会出现ClassCastException异常。
    比如:C类实现了A、B接口,A类型的引用指向了C类型的对象,接口A和接口B并没有继承关系,可以把A类型的引用转换成B类型的引用。并且运行的时候不会出现运行时异常,因为C类同时实现了接口A和接口B。
        代码:  class C implements A,B {}
                A a = new C();
                B b = (B)a;//(可以说A和B都是C的爹)虽然A与B没有继承关系,但是A类型强转成B类型,编译通过,接口允许这么做。运行的时候发现a指向的对象时一个B类型的对象,运行通过。
    C类实现了A接口,B接口是单独定义的一个普通接口,接口A类型的引用指向了C类型的对象,把A类型的引用转换成B类型的引用,编译可以通过(对于接口这种引用数据类型即使没有继承关系也可以强转【在instanceof类型判断的时候后面的是接口类型,没有继承关系也可以编译通过】),但是运行时会抛出异常,因为A是C的爹但是B不是。
        代码:  class C implements A {}
                A a = new C();
                B b = (B)a;//运行抛出类型转换异常,因为a不是一个B类型的对象
15、extends和implements同时出现的时候extends在前implements在后。
16、使用接口写代码的时候,可以使用多态,父类型接口指向子类型对象。
17、类与类之间的关系
   能使用“has a”来描述的,统一以“属性”的方式存在。(比如“人” has a “宠物”)
   能使用“is a”来描述的,都可以设置为继承。(比如“Cat is a Animal”)
   能使用“like a”来描述的,表示“实现关系”
18、接口和类的修饰符只能是“public”或者“默认的”【内部类除外】。
19、class MyClass extends Class1 implements Inter1 {}//接入Inter2是单独定义的一个接口
    //一个类即继承了Class1类又实现了Inter1接口,Class1和Inter1是同级关系。就好像class MyClass implements Inter1,Inter2 {}中的Inter1和Inter2是同级关系
    //“MyClass instanceof Inter2”虽然这个MyClass和Inter2没有继承或实现关系。这个java语句也可以编译通过。
    //Class1 c1 = new MyClass();
    //if (c1 instanceof Inter1) {Inter1 i1 = (Inter1)c1;}//虽然带有强制类型转换(向下类型转换)符,但是并不是向下类型转换,可以理解为同级转换。
    //判断如果c1指向的对象是Inter1类型的对象,编译类型是从Class1类型转换成了Inter1类型(对于接口没有继承关系可以强转,也可以instanceof),但是运行类型一直都是MyClass类型。
20、类和接口类型在相互转换的时候不需要有继承或实现关系也可以强转(包含同级转换)。
    判断一个运行类型是否为接口类型(运行类型 instanceof 接口类型)的时候不需要要有继承关系也可以编译通过。
21、接口中可以包含那些东西?
    Java7中接口里可以包含常量和抽象方法;
    Java8中接口里还可以包含默认方法和静态方法;
    Java9中接口里还可以包私有方法; 
    接口中还可以包含:内部类,内部接口。
    
包机制(package)
1、包机制的作用,是为了方便程序的管理。不同功能的类分别放在不同的包下。(按照功能划分,不同的软件包具有不同的功能)
2、语法结构:“package 包名;”(注意:package语句只能出现在java源代码的第一行)
3、包命名规范:一般采用公司域名倒叙的方式(因为公司域名具有全球唯一性)
    公司域名倒叙 + 项目名 + 模块名 + 功能名
4、对于带有package语句的java程序怎么编译?怎么运行?
    比如:package com.xyh;//类名是Test
    编译:
        javac java源文件的路径
        编译之后直接自己可以生成包:javac -d . java源文件的路径【“-d <directory>”指定放置生成的类文件的位置】
    运行:
        java 包名 + 类名
        java com.xyh.Test
        运行java命令的时候,dos命令窗口必须在com包所在的文件夹,否则会提示“找不到或无法加载主类”;
5、包名要求全部小写(规范),包名也是标识符,必须遵守标识符的命名规则。
6、如果在一个类中使用另一个类,如果两个类在同一个包下那么包名可以省略。

包机制(import)
1、import语句用来完成导入其他类,同一个包下的类不需要导入【如果这个类在java.lang.*;下面不用导入】,不在同一个包下的类需要手动导入。
2、import语句语法格式:
   import  完整的类名;
   import  包名.*; //表示导入该包下的所有类,只会影响编译效率不会影响运行效率,因为编译器在编译的时候会把*变成具体的包名。
3、import语句需要编写到package语句之下,class或者interface之上。
4、java.lang.*; 不需要手动引入,系统自动引入。【language语言包,是Java语言的核心类,不需要手动引入】
5、导入包只能从根目录开始导入。【如果导入的包中“含有包”那么含有的这些包中的类仍然不能用,也不能从现在导入的包中接着导入,只能重新从根目录开始导入】。
6、我们自己些的类中用到了其他的引用数据类型,首先会在“与我们自己写的类同包下找”其他类,第二是在java.lang.*;包下找。
7、不能直接写“import java.*;或者import *;”。“*”只能表示某些类的类名。
8、package 后面写包名;
   import 后面写类名(“*”代表某个包下的所有类);
   import虽然名为“导包”但是实际上是导入的包下的某个类。
9、import可以导入
    包下所有的直接类
    单个类
    静态变量
    静态方法

访问控制权限
1、四种访问控制权限(从上到下范围越来越小)
    public                         公开的     在任何位置都可以访问
    protected                      受保护的   同包中可访问,不同包中有继承关系的子类中可以通过子类对象的引用在子类类体中访问访问(包括this和子类对象)【在父类中声明的protected  类型的属性,不同包中子类继承父类,就相当于在子类中声明了一个private类型的属性】
    什么也不写(不能写“default”)   默认的     只能在同包中访问 
    private                       私有的     只能在本类中访问
2、访问控制权限修饰符可以修饰类、变量、方法、接口。
3、修饰符的范围:private < 缺省 < protected < public
4、修饰类和接口只能使用:public和默认的(default)。【内部类除外】
5、  访问控制修饰符       本类      同包    不同包子类      任意位置
    -------------------------------------------------------------
          public           可以     可以     可以             可以
          protected        可以     可以     可以             不行
           默认             可以     可以     不行             不行
          private          可以     不行     不行             不行
6、protected修饰的东西,可以在不同包的子类“们”类体当中,通过本类(或者本类的子类【因为子类型一定是父类型】)的“对象的引用”或者“类名”。
7、protected修饰的静态的东西,可以在子类中通过“父类名.”的方式访问【但是protected修饰的实例相关的东西不能在子类中通过“父类引用.”的方式访问】


 

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

薛英豪

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值