Java 学习笔记

192 阅读5分钟

Java基础

Java 的一些不了解/易混淆 (相对于Javascript) 的知识

变量类型: 基本类型(整型,浮点型,布尔型,字符型)和引用类型

Tip 与Js不一样的是, String是引用类型, 定义常量使用 关键字final

code

private final String KEY = "66666666";
int page = Integer.parseInt(params.get("page"));
String sortSql = " order by c.LastModifiedDate desc ";

判断两变量相等

浮点数相等比较: 判断之差小于某个特别小的数, 判断引用类型变量内容是否相等: 使用 equals() 方法

Tip 通常把一定不是null的对象放前面 比如 ‘hello’.equals(s)

流程控制 - for each 循环 其他跟js差不多

// 遍历数组ns
public class Main {
    public static void main(String[] args) {
        int[] ns = { 1, 4, 9, 16, 25 };
        for (int n : ns) {
            System.out.println(n);
        }
    }
}

面向对象基础

基本概念

  • 类: 包含描述对象的特征的字段和方法 老虎

  • 实例: new 出来的的实例 老虎小白

  • 方法

  • 构造方法: 创建实例时,通过构造方法来初始化实例, 构造方法名就是类名

  • Tip 注意跟Js的差异。

  • 方法重载: 参数不同的 同名方法

  • : Java定义了一种名字空间,称之为包:package。一个类总是属于某个包,类名(比如Person)只是一个简写,真正的完整类名是包名.类名。

  • 包作用域: 不用public、protected、private修饰的字段和方法就是包作用域

Tip - 作用域

  • public: 公开
  • private: 私有
  • protected: 继承树,同一个包都可

Java支持嵌套类,如果一个类内部还定义了嵌套类,那么,嵌套类拥有访问private的权限

classpath是JVM用到的一个环境变量,它用来指示JVM如何搜索class。

OOP的术语中,我们把Person称为超类(super class),父类(parent class),基类(base class),把Student称为子类(subclass),扩展类(extended class。

继承, 多态

  • 继承: extends 子类自动获得了父类的所有字段,严禁定义与父类重名的字段!
  • Tip 子类无法访问父类的private字段 / 方法。

  • 多态: 针对某个类型的方法调用,其真正执行的方法取决于运行时期实际类型的方法

覆写Override:方法签名相同,并且返回值也相同

  • 向上转型 向下转型: 一个引用类型为Person的变量,能否指向Student类型的实例?

修饰符final

  • final 方法 不可覆写
  • final 类 不可继承
  • final 字段 不能修改

抽象类 - 接口

通过abstract定义的方法是抽象方法,它只有定义,没有实现。抽象方法定义了子类必须实现的接口规范

定义了抽象方法的class必须被定义为抽象类,从抽象类继承的子类必须实现抽象方法

Tip

  1. 抽象类不能有对象,(不能用new此关键字来创建抽象类的对象
  2. 有抽象方法的类一定是抽象类,但是抽象类中不一定有抽象方法;
  3. 抽象类中的抽象方法必须在子类中被重写。

interface,就是比抽象类还要抽象的纯抽象接口,没字段 在接口中,可以定义default方法。

interface Person {
    String getName();
    default void run() {
        System.out.println(getName() + " run");
    }
}

class Student implements Person {
    private String name;

    public Student(String name) {
        this.name = name;
    }

    public String getName() {
        return this.name;
    }
}

Tip

  1. 一个类可以实现多个接口,但只能继承于一个类,所以可以通过这种方式来实现多继承。
  2. 接口中的方法默认修饰符为“public abstract”
  3. 在接口中所有的属性的修饰符都默认为"public static final",

抽象类和接口差异

Tip

  1. 接口强调特定功能的实现,而抽象类强调所属关系。
  2. 接口只有定义,不能有方法的实现,而抽象类可以有定义与实现,方法可在抽象类中实现。
  3. 实现接口的关键字为implements,继承抽象类的关键字为extends。
  4. 一个类可以实现多个接口,但一个类只能继承一个抽象类。所以,使用接口可以间接地实现多重继承。
  5. 接口成员变量默认为public static final,必须赋初值,不能被修改;其所有的成员方法都是public、abstract的。 抽象类中成员变量默认default可在子类中被重新定义,也可被重新赋值;抽象方法被abstract修饰,不能被private、static、synchronized和native等修饰,必须以分号结尾,不带花括号。
  6. 接口被用于常用的功能,便于日后维护和添加删除,而抽象类更倾向于充当公共类的角色,不适用于日后重新对立面的代码修改。功能需要累积时用抽象类,不需要累积时用接口。

静态字段和静态方法

  • 静态字段只有一个共享“空间”,所有实例都会共享该字段
  • 用static修饰的方法称为静态方法。调用静态方法则不需要实例变量,通过类名就可以调用

Tip

  • 静态方法内部,无法访问this变量,也无法访问实例字段,它只能访问静态字段
  • 静态方法经常用于工具类。例如: Arrays.sort(), Math.random() 静态方法也经常用于辅助方法。注意到Java程序的入口main()也是静态方法。
  • interface是一个纯抽象类,所以它不能定义实例字段。但是,interface是可以有静态字段的,并且静态字段必须为final类型
public interface Person {
    // 编译器会自动加上public statc final:
    int MALE = 1;
    int FEMALE = 2;
}

内部类

public class Main {
    public static void main(String[] args) {
        Inner i = new Inner();
        i.hi();
    }

    // private方法:
    private static void hello() {
        System.out.println("private hello!");
    }

    // 静态内部类:
    static class Inner {
        public void hi() {
            Main.hello();
        }
    }
}
// 匿名类
class Outer {
    private String name;

    Outer(String name) {
        this.name = name;
    }

    void asyncHello() {
        // 匿名类
        Runnable r = new Runnable() {
            @Override
            public void run() {
                System.out.println("Hello, " + Outer.this.name);
            }
        };
        new Thread(r).start();
    }
}

观察asyncHello()方法,我们在方法内部实例化了一个Runnable。Runnable本身是接口,接口是不能实例化的,所以这里实际上是定义了一个实现了Runnable接口的匿名类,并且通过new实例化该匿名类,然后转型为Runnable。在定义匿名类的时候就必须实例化它,定义匿名类的写法如下:

Runnable r = new Runnable() {
    // 实现必要的抽象方法...
};

未完待续...