一.java语言的优点,什么机制支撑java具有这么多优点
1.java中JVM的存在语言跨平台
一次编译到处运行,任何一个操作平台上书写的Java代码拿到其他的平台上不需要做任何修改直接可以运行
Java代码是不能直接运行的,首先要编译,编译之后的字节码文件需要运行在JVM上的
我们的计算机是不能直接识别字节码文件的需要有JVm做翻译,我的代码其实是运行在JVM上的
JVM虚拟机是一个标准
2.不需要管理内部不需要手动释放
java中有专门的垃圾回收器,垃圾回收器会根据内部算法每隔一段时候根据算法计算那块空间不用了,自动帮我们回收掉。
System.gc();
Runtime.gc();
当我们自己手动调用的时候,垃圾回收器不一定能工作
3.java提供了字节码验证机制
保证了代码的安全性
4.多线程
java语言的多线程是语言级别的,通过调用java开发人员书写的方法就可以控制线程(相对)
二.进一步了解java程序书写编译以及执行原理
1.Java书写一个类最基本的语法
java源文件:后缀名为.java的文件
三个顶级元素:
(1)class 定义类的关键字 ,Java中所有的代码都必须放在类中,所以类是java中最小的编程单位
[public] class 类名{
属性
方法
构造器
代码块
静态代码块
内部类
}
javac Hello.java Hello.class
java Hello
1.启动JVM
JVM会在执行我们代码之前加载加载资源
-verbose:显示执行的过程
2.加载(运行Hello所需要的其他类,Hello这个程序的本身)
1.什么时候加载hello所需的其他资源类
2.JVM为什么可以找到Hello
加载Hello的时候默认是应用类加载器(本地类加载器)去环境变量中配置CLASSPATH所指定的1位置加载,我们配了一个,默认执行 因此路径改变CLSSPATH就要改变,因此1java中有一个option选项
-cp:执行这个命令的【临时指定】应用类加载器去哪个位置加载你所需要执行的程序
java -cp 需要执行的程序所在的位置 需要执行的程序
(2)package
1.用作:解决同名问题
2.语法:可以有多层包在系统中对应的多级目录,中间使用.作为分隔
3.一旦程序添加了package,那么我们执行程序的时候确定一个程序需要包名加类名,因为一旦添加上package,我们编译过后生成的class文件就在对应目录保存
4.package可有可无,但是如果添加必须放在第一行
5.如果程序中出现了package,那么packsge后面的结构是要作为程序名称的一部分出现,com.briup.day1.Hello,确定需要运行的程序的时候我们需要使用 包名+类名
6.javac Hello.java 如果Hello类中声明包结构,那么这个 命令模式是不会构建包结构,一种解决方案使用mkdir构建包结构,然后把class移动进去,因此javac 提供了一个option
-d path:如果当前正在编译类中有package,自动构建package对应的包结构,同时将这个编译好的class文件放在path中
编译:javac -d bin src/…
运行:java -cp bin …
(3)import
程序书写的语法问题:
1.java源文件
java源文件和源文件中程序之间的关系
如果源文件中的程序使用public,则要求程序的类的名字必须和源文件保持一致。
如果源文件中的程序没有使用public,那么你的类的名字是否和源文件的名字相同没有要求
一个源程序中可以有多个源文件,但是只能有一个public
2.main方法和源文件以及源文件的关系
main方法可以放在源文件中,跟这个源文件是否是public型无关
三、学会使用jar命令进行打包,并且要求运行打包后的程序
jar -cvf 名字.jar 名字.class
这样打包出的jar缺少东西
用压缩工具打开压缩包,里面有一个文件夹 META-INF,里面有一个文件MAINFIST.MF,打开这个文件在最后一行添加
Main-Class: main方法所在的类
重新压缩
执行jar
java -jar Tea.jar
第二种方式:如果不想使用java -jar Tea.jar执行jar中的程序,第二种方式可以把这个jar放在CLASSPATH路径中
CLASSPATH=$CLASSPATH:Tea.jar
java com.briup.day3.Tea
四、类加载器
负责把class文件加载到内存中
启动类加载器 jre/lib/XX.jar
扩展类加载器 jre/lib/ext/xx.jar
应用类加载器CLASSPATH指定的位置
双亲委托:
Java中ClassLoader的加载采用了双亲委托机制,采用双亲委托机制加载类的时候采用如下的几个步骤:
- 当前ClassLoader首先从自己已经加载的类中查询是否此类已经加载,如果已经加载则直接返回原来已经加载的类。
每个类加载器都有自己的加载缓存,当一个类被加载了以后就会放入缓存,等下次加载的时候就可以直接返回了。
-
当前classLoader的缓存中没有找到被加载的类的时候,委托父类加载器去加载,父类加载器采用同样的策略,首先查看自己的缓存,然后委托父类的父类去加载,一直到bootstrp ClassLoader.
-
当所有的父类加载器都没有加载的时候,再由当前的类加载器加载,并将其放入它自己的缓存中,以便下次有加载请求的时候直接返回
如果我们希望在任何一个位置不指定-cp也不更改CLASSPATH的情况下,随时随地执行com.breuo.sday3.Tea
1.com.briup.day3.Tea打成jar包
更改jar包中的信息:Main-Class: com.briup.day3.Tea
2.cp Tea.jar /opt/jdk/jre/lib/ext
五、import:可以出现,也可以不出现
如果一个类需要另外一个类中的方法,如果另外一个类跟当前的类位于同一个包下面,或者另外一个类可当前的类不在同一个包下,而位于java.lang包下,那我们在使用的时候可以不使用import直接用这个类,只要另一个包既不跟我同包,又不在java.lang包下,那么必须要使用import进行导包
位置:package声明下面