由于各个操作系统(windows、linux等)支持的指令集,不是完全一致的,就会让我们的程序在不同的操作系统上要执行不同程序代码,java开发了适用于不同操作系统及位数的java虚拟机来屏蔽系统之间的差异,提供了统一的接口。对于我们java开开发者而言,你只需要在不同的操作系统上安装对应的不同虚拟机、这时你的java程序只要遵循java规范,就可以在所有的操作系统上运行java程序了。
java共有八种基本的数据类型(byte 8位、shot 16位、int 32位、long 64位、float 32位、double 64位、char 16位、boolean 1位)。
有四大基本特征:封装、抽象、继承、多态。
封装性:即将对象封装成一个高度自治和相对封闭的个体,对象状态(属性)由这个对象自己的行为(方法)来读取和改变。
抽象:就是找出一些事物的相似和共性之处,然后将这些事物归为一个类,这个类只考虑这些事物的相似和共性之处,并且会忽略与当前主题和目标无关的那些方向,将注意力集中在与当前目标有关的方面,就是把现实生活中的对象,抽象为类。
继承:在定义和实现一个类的时候,可以在一个已经存在的类的基础之上来进行,把这个已经存在的类所定义的内容作为自己的内容,并可以加入若干新的内容,或修改原来的方法使之更合适特殊的需要,这就是继承,类似于继承遗产。
多态:指程序中定义的引用变量所指向的具体类型和通过该引用变量发出的方法调用在编程时并不确定,而是在程序运行期间才确定,即一个引用变量到底会指向哪个类的实例对象,该引用变量发出的方法调用到底是哪个类中实现的方法,必须在由程序运行期间才能决定。靠的是父类或接口定义的引用变量可以指向子类或具体实现类的实例对象,而程序调用的方法在运行期间才动态绑定,就是引用变量所指向的具体实例对象的方法,也就是内存里正在运行的那个对象的方法,而不是引用变量的类型中定义的方法。
为什么需要包装类型?因为java是一个面向对象的语言,而基本的数据类型,不具备面向对象的特性,比如null、max、min。
缓存值:对象缓存,Integer i = 1;Integer j = 1;i == j;
装箱:把基本的数据类型转换成对应的包装类型。列如:Integer.valueof(1)、Integer i = 1,自动装箱,实际上在编译时会调用Integer.valueOf方法来装箱。
拆箱:就是把包装类型换为基本数据结构类型,基本数据类型:(名称 = 对应的包装类型)。自动拆箱(Integer i = 1;int j = i;),在自动拆箱中实际上会在编译调用intValue,手动拆箱(int j = i.intValue())。
"=="用来判断两个变量之间的值是否相等。变量就可以分为基本数据类型变量,引用类型,如果是基本数据类型的变量直接比较值,而引用类型要比较对应的引用的内存的首地址。
"equals"用来比较两个对象长得是否一样。判断两个对象的某些特征是否一样。实际上就是调用对象的equals方法进行比较。
在java中提供三个类String、StringBuilder、StringBuffer来表示和操作字符串,字符串就是多个字符的集合。
String:是内容不可变的字符串,String底层使用了一个不可变的字符数组(private final char value[]; )。
StringBuilder和StringBuffer:是内容可变的字符串,StringBuilder和StringBuffer底层使用的是可变的字符数组。(没有使用final来修饰,char[] value)。
经典例子:
1、String进行拼接String c = “a” + ”b“;拼接时会"a"会声明一个对象,"b"会声明一个对象,一次类推,很影响性能。
2、StringBuilder和StringBuffer进行拼接StringBuilder sb = new StringBuilder();sb.apend(“a”).apend(“b”);这种方式拼接对象只会创建一次。
结论:拼接字符串不能使用String进行拼接,要使用StringBuilder或者StringBuffer。
额外:StringBuilder是线程不安全的,效率较高,而StringBuffer是线程安全的,效率较低,它使用的是synchronized同步锁。
java中的集合分为value、key-value(conllection Map)两种。
存储value有分为List和Set,详细如下:
1.List是有序的,可以重复的。
2.Set是无序的,不可以重复的。根据equals和hashcode判断,也是如果一个对象存储在Set中,必须重写equeals和hashcode方法。
存储key-value的为map。
List常用的ArrayList和LinkedList使用场景?
ArrayList底层使用的是数组,LinkedList使用的是链表。
数组查询具有所有查询特定元素比较快,而插入和删除和修改比较慢(数组在内存中是一块连续的内存,如果插入或删除是需要移动内存)。
链表不要求内存是连续的,在当前元素中存放一个或上一个元素的地址。查询时需要从头部开始,一个一个的找,所以查询效率低。插入时不需要移动内存,只需改变引用指向即可,所以插入或者删除的效率高。
结论:ArrayList使用在查询比较多,但是插入和删除比较少的情况,而LinkedList使用在查询比较少而插入和删除比较多的情况。
相同点:HashMap和HashTable都可以使用来存储key-value的数据。
区别:
1.HashMap是可以把null作为key或者value的,而HashTable是不可以的。
2.HashMap是线程不安全的,但是效率高,HashTable是线程安全的,但是效率低。
结论:我想要效率高,同时线程还是安全的,可以使用ConcurrentHashMap,通过把整个Map分为n个Segment(类似HashTable),可以提供相同的线程安全,但是效率提升N被,默认提升16倍。
我们拷贝的文件不确定是只包含字符流,有可能有字节流,比如(图片、声音、图像等),为考虑通用性,一般采用字节流。
实现方式:
1.通过继承Thread类实现一个线程。
2.通过实现Runnable接口实现一个线程。
继承的扩展性不强,java只支持单继承,如果一个类继承Thread就不能继承其他类。
启动过程:
Thread thread = new Thread(继承了Thread的对象/实现了Runnable的对象);
thread.setName(“设置一个线程名”);//每个线程都会打印日志,区分是哪一个线程打印可以使用setName(),这是一种规范,在创建线程完成后,都需要设置名称。
thread.start();//启动线程使用start()方法,而启动了以后执行的是run方法。
JDK5中增加了Doug Lea的并发库,这一引进给java线程的管理和使用提供了强大的便利性。java.util.current包中提供了对线程优化、管理的各项操作,使得线程的使用变得得心应手。该包提供了线程的运行,线程池的创建,线程池生命周期的控制。
Java通过Executors提供了四种线程池,分别为:
1.newCachedThreadPool创建一个可缓存线程池,如果线程池长度超过处理需要,可灵活回收空闲线程,若无可回收,则新建线程。
2.newFixedThreadPool创建一个定长线程池,可控制线程池最大并发数,超出的线程会在队列中等待。
3.newScheduledThreadPool创建一个定长线程池,支持定时及周期性任务执行。
4.newSingleThreadExecutor创建一个单线程化的线程池,它只会用唯一的工作线程来执行,保证所有任务按照指定顺序(FIFO,LIFO,优先级)执行。
线程池的作用:
1.限定线程个数,不会导致由于线程过多导致系统运行缓慢或崩溃。
2.线程池不需要每次都去创建或者销毁,为了节约资源。
3.线程池不需要每次都去创建,响应时间更快。
连接池简单介绍:
使多个请求能够共享同一个连接。连接池很好地满足了这样的要求,由连接池来管理数据连接的建立和注销,初始化时建立多条连接,以供客户使用。由连接池来管理数据库连接的建立和注销。连接池初始化时建立多条连接,供给不同的请求使用,多个请求可以共享同一连接,这样做,就可以减少打开、关闭数据库连接的操作,从而改善了系统的性能。
连接池的作用以及优势:
1.资源重用(由于数据库连接得到重用,避免了频繁创建、释放连接引起的大量性能开销。在减少系统消耗的基础上,另一方面也增进了系统运行环境的平稳性(减少内存碎片以及数据库临时进程/线程的数量))。
2.更快的系统响应速度(数据库连接池在初始化过程中,往往已经创建了若干数据库连接置于池中备用。此时连接的初始化工作均已完成。对于业务请求处理而言,直接利用现有可用连接,避免了数据库连接初始化和释放过程的时间开销,从而缩减了系统整体响应时间)。
3.新的资源分配手段(对于多应用共享同一数据库的系统而言,可在应用层通过数据库连接的配置,实现数据库连接池技术,几年钱也许还是个新鲜话题,对于目前的业务系统而言,如果设计中还没有考虑到连接池的应用,那么…….快在设计文档中加上这部分的内容吧。某一应用最大可用数据库连接数的限制,避免某一应用独占所有数据库资源)。
4.统一的连接管理,避免数据库连接泄漏(在较为完备的数据库连接池实现中,可根据预先的连接占用超时设定,强制收回被占用连接。从而避免了常规数据库连接操作中可能出现的资源泄漏)。
设计模式就是经过前人无数次的实践总结出来的,设计过程中可以反复使用的、可以理解特定问题的设计方法。
单例模式(懒汉和饿汉)。
工厂模式(Spring IOC就是使用了工厂模式,对象的创建给工厂去创建)。
代理模式(Spring AOP就是使用的动态代理模式)。
Get和Post请求都是Http的不同请求方式,用户通过不同的请求方式完成对资源(Url)的不同操作。Get、Post、Put、Delete就对应着对资源的查、改、增、删四个操作,具体操作来讲GET一般用于获取/查询资源信息,而POST一般用户更新资源。
1.Get请求提交的数据会在地址栏显示出来,而Post请求的数据不会在地址栏显示出来。Get提交,请求数据会附在URL之后(就是把数据放置在Http协议头中),以’?'分割Url和传输数据,多个参数用&连接;Post请求提交的数据放置在HTTP协议包的包体中。因此,Get提交的数据会在地址栏显示出来,而Post提交,地址栏则不会改变。
2.传输数据的大小,Http Get请求由于浏览器对地址长度的限制而导致传输的数据有限制。而Post请求不会因为地址栏长度限制而导致传输数据大小限制。
3.安全性,Post的安全性要比Get要高。由于数据会在地址栏显现,所以可以通过历史记录找到密码等关键信息。
Servlet(Server Applet),全称Java Servlet,是用Java编写的服务端程序。而这些Servlet都要实现Servlet这个接口。其主要功能在于交互式的浏览和修改数据,生成动态的Web内容。Servlet运行于支持Java的应用服务器中。
使用流程:HttpServlet重写doGet和doPost方法或者你也可以重写Service方法完成对Get和Post请求的响应。
Servlet有良好的生存期的定义,包括加载和实例化、初始化、处理请求以及服务结束。这个生存期由javax.servlet.servlet接口的init、service和destroy方法表达。
Servlet启动时,开始加载Servlet生命周期开始。Servlet被服务器实例化后,容器运行其init方法,请求到达时运行其service方法,service方法自动派遣运行与请求对应的doXXX方法(doGet、doPost)等,当服务器决定将实例销毁的时候(服务关闭)调用其destroy方法。
执行流程:加载Servlet的class->实例化Servlet->调用Servlet的init完成初始化->响应请求(Servlet的service方法)->Servlet容器关闭时(Servlet的destroy方法)。
1、forward是服务器端的转向,而redirect是客户端的转向。
2、使用forward浏览器的地址不会发生改变,而redirect会发生改变。
3、forward是一次请求完成,而redirect是重新发起请求。
4、forward是在服务器端完成,而不用客户端重新发起请求,效率比较高。
相同点:JSP是Servlet技术的扩展,所有的JSP文件都会被翻译为一个继承HttpServlet的类,也就是JSP最终也是一个Servlet,这个Servlet对外提供服务。
不同点:JSP侧重于视图,Servlet侧重于控制逻辑。Servlet如果要实现html功能,必须使用Write输出对应的html,比较麻烦,而JSP的情况是java和html可以组合成一个扩展名为.jsp的文件,做界面展示比较方便而嵌入逻辑比较复杂。
JSP共有9个内置对象:
1、request:用户请求,此请求会包含来自Get/Post请求的参数。
2、response:页面传回用户端的回应。
3、pageContext:网页的属性是在这里进行管理。
4、session:与请求有关的会话期。
5、application:servlet正在执行的内容。
6、out:用来传送回应的输出。
7、config servlet:config servlet架构部件。
8、page JSP:网页本身。
9、exception:针对错误页面,未捕捉的例外。
四大作用域:
pageContext、request、session、application可以通过jstl从四大作用域获值。
JSP传递值:request、session、application、cookie。
Session和Cookie都是会话(Session)跟踪技术,用来跟踪用户的整个会话。Cookie通过在浏览器记录信息确定用户身份,Session通过在服务端记录信息确定身份。但是Session的实现依赖于Cookie,SessionId(session的唯一标识需要存放在客户端)。
1、Cookie数据存放在客户端的浏览器上,而session数据存放在服务器上。
2、Cookie不是很安全,别人可以分析存放在本地的Cookie进行Cookie欺骗,考虑到安全应当使用Session。
3、Session会在一定时间内保存在服务器上。当访问增多时,比较占用服务器的性能,考虑到减轻服务端的压力,应当根据场景适当的使用Cookie。
4、单个Cookie保存的数据不能超过4K,很多浏览器都限制一个站点最多保存20个Cookie。
5、将登陆信息等重要信息保存为Session,将比如购物车信息可以存放到Cookie中。
M(Model)模型,javabean。
V(View)视图,html、jsp、volicity、freemaker。
C(Controller)控制器,Servlet、Action。
JSP+Servlet+JavaBean最经典的MVC模式,实际上就是Model2的实现方式,就是把视图和逻辑隔离出来。
Model1的方式:jsp+servlet+dao。
Model2的方式:jsp+servlet+service+dao。
Struts2和SpringMVC框架的方式:jsp+核心控制器+action+javabean。