JAVA学习笔记
主要记录,在学习java时,与之前学习其他语言有比较大差异的地方:
1. Java 源程序与编译型和解释型语言的区别
编译型语言
定义: 在程序运行之前,通过编译器将源程序编译成机器码(可运行的二进制代码),以后执行这个程序时,就不用再进行编译了。
优点: 编译器一般会有预编译的过程对代码进行优化。因为编译只做一次,运行时不需要编译,所以编译型语言的程序执行效率高,可以脱离语言环境独立运行。
缺点: 编译之后如果需要修改就需要整个模块重新编译。编译的时候根据对应的运行环境生成机器码,不同的操作系统之间移植就会有问题,需要根据运行的操作系统环境编译不同的可执行文件。
总结: 执行速度快、效率高;依靠编译器、跨平台性差些。
代表语言:C、C++、Pascal、Object-C以及Swift。
解释型语言
定义: 解释型语言的源代码不是直接翻译成机器码,而是先翻译成中间代码,再由解释器对中间代码进行解释运行。在运行的时候才将源程序翻译成机器码,翻译一句,然后执行一句,直至结束。
优点: 有良好的平台兼容性,在任何环境中都可以运行,前提是安装了解释器(虚拟机)。灵活,修改代码的时候直接修改就可以,可以快速部署,不用停机维护。
缺点: 每次运行的时候都要解释一遍,性能上不如编译型语言。
总结: 执行速度慢、效率低;依靠解释器、跨平台性好。
代表语言: JavaScript、Python、Erlang、PHP、Perl、Ruby。
混合型语言
定义: 既然编译型和解释型各有缺点就会有人想到把两种类型整合起来,取其精华去其糟粕,就出现了半编译,半解释型语言。
Java即是编译型的,也是解释型语言,总的来说Java更接近解释型语言。
可以说它是编译型的。 因为所有的Java代码都是要编译的,.java不经过编译就什么用都没有。同时围绕JVM的效率问题,会涉及一些如JIT、AOT等优化技术,例如JIT技术,会将热点代码编译成机器码。而AOT技术,是在运行前,通过工具直接将字节码转换为机器码。
可以说它是解释型的。 因为Java代码编译后不能直接运行,它是解释运行在JVM上的,所以它是解释运行的。
2. 构造类方法时,使用类名做作构造方法名:
比如一个创建一个Dog类,像其他语言一般都会有一个固定的方法名:比如javascript的constructor,swift的init方法。
public class Dog {
String bread;
int size;
// 初始化方法
public Dog(String bread, int age) {
this.bread = bread;
this.age = age;
}
}
3. 源文件声明规则
当在一个源文件中定义多个类,并且还有import语句和package语句时,要特别注意这些规则。
● 一个源文件中只能有一个 public 类 (每个编译单元(文件)都只能有一个public类,这表示,每个编译单元都有单一的公共接口,用public类来表现)
● 一个源文件可以有多个非 public 类
● 源文件的名称应该和 public 类的类名保持一致。例如:源文件中 public 类的类名是 Employee,那么源文件应该命名为Employee.java。
● 如果一个类定义在某个包中,那么 package 语句应该在源文件的首行。
● 如果源文件包含 import 语句,那么应该放在 package 语句和类定义之间。如果没有 package 语句,那么 import 语句应该在源文件中最前面。
4. switch case
跟OC类似,每个case后面如果不写break的话后续所有case的值都会输出,swift语言就可以忽略这些break代码。
5. finalize() 方法
Java 允许定义这样的方法,它在对象被垃圾收集器析构(回收)之前调用,这个方法叫做 finalize( ),它用来清除回收对象。
例如,你可以使用 finalize() 来确保一个对象打开的文件被关闭了。
在 finalize() 方法里,你必须指定在对象销毁时候要执行的操作。类似于swift中的dealloc方法。
finalize() 一般格式是:
protected void finalize()
{
// 在这里终结代码
}
关键字 protected 是一个限定符,它确保 finalize() 方法不会被该类以外的代码调用。
6. java方法
可变参数:
OC写法:
- (void)testVarargs: (int)nums, ...{
NSLog(@"%d",nums);
}
java写法:
private void testVarags(int... nums) {
System.out.println(nums);
}
swift写法:
private func testVarargs(nums: Int...) {
print("nums: (nums)")
}
看着java像是从OC到Swift的一个中间状态的一种写法。
7. java的继承
类的继承是单一继承,也就是说,一个子类只能拥有一个父类,所以 extends 只能继承一个类。
使用 implements 关键字可以变相的使java具有多继承的特性,使用范围为类继承接口的情况,可以同时继承多个接口(接口跟接口之间采用逗号分隔)。
public interface A {
public void eat();
public void sleep();
}
public interface B {
public void show();
}
public class C implements A,B {
}
8. 抽象类
在 Java 语言中使用 abstract class 来定义抽象类。
● 1. 抽象类不能被实例化(初学者很容易犯的错),如果被实例化,就会报错,编译无法通过。只有抽象类的非抽象子类可以创建对象。
● 2. 抽象类中不一定包含抽象方法,但是有抽象方法的类必定是抽象类。
● 3. 抽象类中的抽象方法只是声明,不包含方法体,就是不给出方法的具体实现也就是方法的具体功能。
● 4. 构造方法,类方法(用 static 修饰的方法)不能声明为抽象方法。
● 5. 抽象类的子类必须给出抽象类中的抽象方法的具体实现,除非该子类也是抽象类。
9. java 接口(interface)
接口(英文:Interface),在JAVA编程语言中是一个抽象类型,是抽象方法的集合,接口通常以interface来声明。一个类通过继承接口的方式,从而来继承接口的抽象方法。与iOS中的协议类似。
接口与类相似点:
● 一个接口可以有多个方法。
● 接口文件保存在 .java 结尾的文件中,文件名使用接口名。
● 接口的字节码文件保存在 .class 结尾的文件中。
● 接口相应的字节码文件必须在与包名称相匹配的目录结构中。
接口与类的区别:
● 接口不能用于实例化对象。
● 接口没有构造方法。
● 接口中所有的方法必须是抽象方法,Java 8 之后 接口中可以使用 default 关键字修饰的非抽象方法。
● 接口不能包含成员变量,除了 static 和 final 变量。
● 接口不是被类继承了,而是要被类实现。
● 接口支持多继承。
接口特性:
● 接口中每一个方法也是隐式抽象的,接口中的方法会被隐式的指定为 public abstract(JDK 1.9 以后,允许将方法定义为 private,使得某些复用的代码不会把方法暴露出去)。
● 接口中可以含有变量,但是接口中的变量会被隐式的指定为 public static final 变量(并且只能是 public,用 private 修饰会报编译错误)。
● 接口中的方法是不能在接口中实现的,只能由实现接口的类来实现接口中的方法。(JDK 1.8 以后,接口允许包含具体实现的方法,该方法称为"默认方法",默认方法使用 default 关键字修饰)。
抽象类和接口的区别:
● 抽象类中的方法可以有方法体,就是能实现方法的具体功能,但是接口中的方法不行。
● 抽象类中的成员变量可以是各种类型的,而接口中的成员变量只能是 public static final 类型的。
● 接口中不能含有静态代码块以及静态方法(用 static 修饰的方法),而抽象类是可以有静态代码块和静态方法。
● 一个类只能继承一个抽象类,而一个类却可以实现多个接口。