什么是不可变对象
- 不可变对象是指对象一旦被创建,状态就不能再改变。任何修改都会创建一个新的对象,如String,Integer及其它包装类
& 和 && 的区别
- &是位运算符,而&&是逻辑运算符。逻辑运算符具有短路特性,而&不具备短路特性
final与static关键字可以用于哪里?他们的作用是什么
- final:修饰变量,值不可被修改;修饰方法,方法无法被重写;修饰类无法被继承
- static修饰变量,静态变量可直接用类名访问;修饰方法,可直接通过类名调用
抽象类是否可以继承具体类
- 抽象类可以继承具体类,但前提是实体类必须有明确的构造函数
抽象类中是否可以用静态的main方法
抽象类中可以用静态的main方法,如果定义一个抽象方法test(),并且在main方法中用到这个抽象方法test()时就不能用了
HashMap和HashTable的区别
- HashTable是线程安全的,HashMap不是;HashMap中允许存在null键和null值,而HashTable中不允许
什么是类的反射机制
- 动态获得对象
- 通过类(Class对象),可以得出当前类的fields、method、construtor、interface、superClass、modified等,同时可以通过类实例化一个实例、设置属性、唤醒方法。Spring中一切都是反射、struts、Hibernate等都是通过反射进行开发的
类的反射机制中的包及核心类
- java.lang.Class
- java.lang.refrection.Method
- java.lang.refrection.Field
- java.lang.refrection.Constructor
- java.lang.refrection.Modifier
- java.lang.refrection.Interface
Servlet的生命周期
- Servlet生命周期包括三部分:
- 初始化:web容器加载servlet,调用init()方法
- 处理请求:通过调用service()方法实现,根据请求的不同调用不同的do***()(doGet()或doPost())方法
- 销毁:当服务器决定将实例销毁的时候调用其destroy()方法
什么情况下调用doGet()和doPost()?
- jsp页面中的form标签里的method属性为get时调用doGet(),为post时调用doPost()
JSP与Servlet有什么区别
- Servlet是服务器端的程序,动态生成html页面发送到客户端,但是这样程序里会有很多out.println(),java与html语言混在一起很乱,所以后来sun公司推出了JSP,其实JSP就是Servlet,每次运行的时候JSP都首先被编译成servlet文件,然后再被编译成.class文件运行。有了JSP,在MVC项目中servlet不再负责动态生成页面,转而去负责控制程序逻辑的作用,控制JSP与JavaBean之间的流转
四种会话跟踪技术作用域
- page:一个页面
- request:一次请求
- session:一次会话
- application:服务器从启动到停止
四种会话跟踪技术
- page:是代表与一个页面相关的对象和属性。一个页面由一个编译好的Java Servlet类(可以带有任何的include指令,但是没有include动作)表示。这即包括Servlet又包括被编译成Servlet的页面
- request是代表与web客户端发送的一个请求相关的对象和属性。一个请求可以跨越多个页面,涉及多个web组件
- session代表与用于某个web客户端的一个用户体验相关的对象和属性,一个web会话可以也经常会跨越多个客户机请求
- application是代表与整个web应用程序相关的对象和属性,这实际上是跨越多个web应用程序,包括多个页面、请求和会话的一个全局作用域
forward和redirect的区别
转发与重定向
- 从地址栏显示来说
1)forward是服务器请求资源,服务器直接访问目标地址的URL,把那个URL的响应内容读取过来,然后把这些内容再发给浏览器。浏览器不知道服务器发送的内容是从哪里来的,所以它的地址栏还是原来的地址。
2)redirect是服务端根据逻辑,发送一个状态码,告诉浏览器重新去请求那个地址。所以地址栏显示的是新的URL。 - 从数据共享来说
1)forward:转发页面和转发到的页面可以共享request里面的数据
2)redirect:不能共享数据 - 从运用地方来说
1)forward:一般用于用户登录的时候,根据角色转发到相应的模块
2)redirect:一般用于用户注销登录时返回主页和跳转到其他的网站等 - 从效率来说
1)forward:高
2)redirect:低
为什么在session少放对象
- 因为session底层是由cookie实现的,当客户端的cookie被禁用后,session也会失效,且应尽量少向session中保存信息,session的数据保存在服务器端
JSP和Servlet有哪些相同点和不同点
- JSP时Servler技术的扩展,本质上是Servlet的简易方式,更强调应用的外部表达。JSP编译后是"类 Servlet"。Servlet和JSP最主要的不同点在于Servlet的应用逻辑是在Java文件中,并且完全从表达层中HTML里分离出来,而JSP是Java和HTML结合成一个扩展名为.jsp的文件,JSP侧重于视图,Servlet侧重于控制逻辑。
Tomcat有几种部署项目的方式
-
部署项目的第一种方式(项目直接放入webapps目录中)
1、将编写并编译好的web项目(注意要是编译好的,如果是eclipse,可以将项目达成war包放入),放入到webapps中
image.png
2、启动tomcat服务器(双击tomcat路径\bin目录下的startup.bat,启动服务器)
3、在浏览器输入:http://localhost:端口号/项目名/访问的文件名
-
部署项目的第二种方式(修改conf/server.xml文件)
1、打开tomcat下conf/server.xml,在<Host></Host>标签之间输入项目配置信息
image.png
参数说明:
① path:浏览器访问时的路径名
2、双击startup.bat,启动tomcat服务器然后在浏览器输入访问的项目名称路径
② docBase:web项目的WebRoot所在的路径,注意是WebRoot的路径,不是项目的路径。其实就是编译后的项目
③reloadble:设定项目有改动时,tomcat是否重新加载该姓名
image.png
注意:如果你配置的 path="/xx",那么访问的时候就是这样:
-
部署项目的第三种方式(E:\apache-tomcat-9.0.12\conf\Catalina\localhost)
1、进入到E:\apache-tomcat-9.0.12\conf\Catalina\localhost目录,新建一个项目名.xml文件
image.png
2、在那个新建的xml中间中,添加下面配置语句(和上面的是一样的,但是不需要 path 配置,加上也没什么用)
<Context docBase="D:/WebProject" reloadable="true" />
3、在浏览器输入路径:localhost:8080/xml文件名/访问的文件名
总结:
第一种方法比较普通,但是我们需要将编译好的项目重新 copy 到 webapps 目录下,多出了两步操作
第二种方法直接在 server.xml 文件中配置,但是从 tomcat5.0版本开始后,server.xml 文件作为 tomcat 启动的主要配置文件,一旦 tomcat 启动后,便不会再读取这个文件,因此无法再 tomcat 服务启动后发布 web 项目
第三种方法是最好的,每个项目分开配置,tomcat 将以\conf\Catalina\localhost 目录下的 xml 文件的文件名作为 web 应用的上下文路径,而不再理会 <Context>中配置的 path 路径,因此在配置的时候,可以不写 path。
通常使用第三种方法
Servlet相关API
-
request.getParameter()
返回客户端的请求参数的值 -
request.getParameterNames()
返回所有可用属性名的枚举 -
request.getParameterValues()
返回包含参数的所有值的数组
-
request.getAttribute()
和request.getParameter()
区别
用途上:-
request.getAttribute()
,一般用于获取request域对象的数据(在跳转之前把数据实用setAttribute来放到request对象上) -
request.getParameter()
,一般用于获取客户端提交的参数
存储数据上: -
request.getAttribute()
可以获取Object对象 -
request.getParameter()
只能获取字符串(这就是为什么它一般用于获取客户端提交数据)
-
session和cookie的区别
- 从隐式安全上比较
- cookie存储在浏览器中,对客户端是可见的。信息容易泄露出去。如果使用cookie最好将cookie加密
- session存储在服务器上,对客户端是透明的。不存在敏感信息泄露问题
- 从有效期上比较
- cookie保存在硬盘中,只需要设置maxAge属性为比较大的正整数,即使关闭浏览器,cookie还是存在的
- session的保存在服务器中,设置maxInactiveInterval属性值来确定session的有效期。并且session依赖于名为JSESSIONID的cookie,该cookie默认的maxAge属性为-1。如果关闭了浏览器,该session虽然没有从服务器中消亡,但也失效了。
Servlet安全性问题
- 由于Servlet是单例的,当多个 用户访问Servlet的时候,服务器会为每个用户创建一个线程。当多个用户并发访问Servlet共享资源的时候就会出现线程安全问题。
- 规则:
- 如果一个变量需要多个用户共享,则应当在访问该变量的时候,加同步机制
synchronized(对象){}
- 如果一个变量不需要共享,则直接在doGet()或者doPost(),这样不会存在线程安全问题
- 如果一个变量需要多个用户共享,则应当在访问该变量的时候,加同步机制
JSP有哪些动作以及作用是什么?
-
jsp:include
:在页面被请求的时候引入一个文件 -
jsp:useBean
:寻找或者实例化 一个JavaBean -
jsp:setProperty
:设置JavaBean的属性 -
jsp:getProperty
:输出某个JavaBean的属性 -
jsp:forwar
:把请求转到一个新的页面 -
jsp:plugin
:根据浏览器类型为Java查询生成OBJECT或EMBED标记 -
jsp:param
:动作(传递参数):到达跳转页面也可以通过request.getParameter("参数名")方式取出参数值
jsp有哪些内置对象
- request
- response
- pageContext
- session
- application
- out
- config
- page
- exception
如何配置Servlet
- Servlet的声明:
<servlet>
<servlet-name>servlet的名字</servlet-name>
<servlet-class>servlet的完整类名</servlet-class>
</servlet>
- Servlet访问方式的声明
<servlet-mapping>
<servlet-name>servlet的名字(应该和声明的名字保持一致)</servlet-name>
<url-pattern>访问路径</url-pattern>
</servlet-mapping>
JSP中动态include和静态include有什么区别?
- 静态include指令用于把另一个页面包含到当前页面中,在转换成servlet的时候包含进去的。
动态include用jsp:include动作失效<jsp:include page="included.jsp" flush="true"/>它总是会检查所含文件中的变化,适合用于包含动态页面,并且可以带参数 - 静态包含:将两个页面编译成一个class,里面的资源可共享
动态包含:将两个页面编译成两个独立的class,里面的资源无法共享
JSP如何处理JSON
- 在JSP总处理JSON,通常需要配套使用jQuery控件,并且导入一些Common jar包。使用jQuery控件是因为它能有效的解析并且展示JSON数据。
如何处理Servlet的线程不安全问题
- 不适用字段变量
- 使用final修饰变量
- 线程安全就是多线程操作同一个对象不会有问题,线程同步一般来保护线程安全
判断浏览器是否支持Cookie
- 可以使用JavaScript的方法navigator.cookieEnabled判断浏览器是否支持cookie
JSP页面跳转
- JSP页面跳转有两种方式,forward和redirect(转发和重定向)
404、500、304分别是什么意思
- 404:找不到URL请求的路径,一般是工程名不对或者拼写错误
- 500:服务器内部错误,一般是服务器内部代码编写错误,也有可能是抛异常导致
- 304:表示浏览器端有缓存,并且服务端未更新,不用向服务器端请求资源
Servlet监听器的作用
- Servlet监听器对特定的事件进行监听,当产生这些事件的时候,会执行监听器的代码。可以对应用的加载、卸载,对session的初始化、销毁,对session中值的变化等事件进行监听
四大共享范围:
- application:全局作用范围,整个应用程序共享,就是在部署文件总的同一个webApp共享,生命周期为:应用程序启动到停止
- session:会话作用域,当用户首次访问时,产生一个新的会话,以后服务器就可以记住这个会话状态。生命周期:会话超时,或者服务器强制使session会话失效
- request:请求作用,就是客户端的一次请求
- page:一个JSP页面
以上作用范围越来越小,request和page的生命周期都是短暂的,它们之间的区别就是:一个request可以包含多个page页(include、forward和filter)
我们没有写Servlet的构造方法,那么容器是怎么创建Servlet的实例?
- 容器会自动为Servlet写一个无参的构造方法,并通过Class.forName(className).newInstance()来创建Servlet实例。
Document对象常用方法:
-
getElementById()
:返回拥有指定id的第一个对象的引用 -
getElementsByName()
:返回带有指定名称的对象的集合 -
getElementsByTagName()
:返回带有指定标签名的对象的集合 -
getElementsByClassName()
:返回带有指定类名的对象的集合 -
write()
:向文档写文本、HTML或JavaScript代码
spring中BeanFactory和ApplicationContext的区别
BeanFactory | ApplicationContext |
---|---|
使用懒加载 | 使用即使加载 |
使用语法显示提供资源对象 | 自己创建和管理资源对象 |
不支持国际化 | 支持国际化 |
不支持基于依赖的注解 | 支持基于依赖的注解 |
Ajax的原理和实现步骤
-
Ajax即"Asynchronous JavaScript And XML"(异步JavaScript和XML)
,通过在后台与服务器进行少量数据交换,可以使网页实现异步更新。这意味着可以在不重新加载整个网页的情况下,对网页的某部分进行跟新 - 原理:HTTP协议的异步通信
- 实现步骤:
创建XMLHttpRequest对象
注册回调函数
设置连接信息
发送数据,与服务器开始交互
接受服务器返回数据
数据库的分类及常用的数据库
- 数据库分为:关系型数据库和非关系型数据库
- 关系型:MySQL、Oracle、SQL server等
- 非关系型:redis、memcache、mogodb、Hadoop等
事务四个基本特征或ACID特性
事务必须满足四大特征:原子性、一致性、隔离性、持久性/持续性
- 原子性:表示事务内操作不可分割。要么都成功、要么都是失败
- 一致性:要么都成功、要么都是失败。后面的失败了要对前面的操作进行回滚
- 隔离性:一个事务开始后,不能被其他事务干扰
- 持久性/持续性:表示事务开始了,就不能终止
如何实现对象克隆
- 1.实现Cloneable接口并重写Object类中的clone()方法
- 2.实现Serializable接口,通过对象的序列化和反序列化实现克隆
线程的生命周期
- 新建(New)、就绪(Runnable)、运行(Running)、阻塞(Blocked)和死亡(Dead)五种状态
Java类实现序列化有几种方法
- 实现Serializable接口或实现Externalizable
在Collection框架中实现排序,要实现什么样的接口
- Collection框架中实现比较要实现Comparable接口或Comparator接口,并实现比较方法
解释Serializable接口的作用
- Serializable接口描述启动其序列化功能,未实现此接口的类将无法使其任何状态序列化或反序列化。Serializable接口没有方法或字段,仅用于标识可序列化,标识实现了该接口的对象属性可被序列化
集合
- 集合类存放于java.util包中
- 集合类存放的都是对象的引用,,而非对象本身,出于表达上的便利,称集合中的对象就是指集合中对象的引用(reference)
- 集合类型主要有3种:set、list和map
- 集合接口分为:Colleection和Map,list、set实现了Collection接口
实现Set接口的常用类有
- HashSet类(底层数据结构是数组 + 单链表 + 红黑树,无序)
- LinkedHashSet(底层数据结构是数组 + 单链表 + 红黑树 + 双向链表,无序)
- TreeSet(底层数据结构红黑树,有序)
什么是不可变对象
- 不可变对象是指对象一旦被创建,状态就不能再改变。任何修改都会创建一个新的对象,如String、Integer及其它包装类
Java中的final关键字有哪些用法
- 修饰类:表示该类不能被继承
- 修饰方法:表示方法不能被重写
- 修饰变量:表示变量只能一次赋值以后值不能被修改(常量)
常见的运行时异常
- ArithmeticException(算术异常)
- ClassCaseException(类转换异常)
- IllegalArgumentException(非法参数异常)
- IndexOutOfBoundsException(下标越界异常)
- NullPointerException(空指针异常)
什么是线程安全
- 如果代码所在的进程中有多个线程在同时运行,而这些线程可能会同时运行这段代码。如果每次运行结果和单线程运行的结果是一样的,而且其他的变量的值也和预期的是一样的,就是线程安全的。一个线程安全的计数器类的同一个实例对象在被多个线程使用的情况下也不会出现计算失误。
Vector是一个线程安全类?
- Vector是用同步方法来实现线程安全的,而和它相似的ArrayList不是线程安全的
集合框架中的泛型有什么优点
- 避免了在运行时出现ClassCaseException
- 使代码更整洁
- 不会产生类型检查的字节码指令,给运行时带来好处
如果两个建的hashcode相同,如何获取值对象
- 当我们调用get()方法,HashMap会使用键对象的hashcode找到bucket位置,然后会调用keys.equals()方法去找到链表中正确的节点,最终找到要找的值对象
为什么Map接口不继承Collection接口
- 尽管Map接口和它的实现也是集合框架的一部分,但Map不是集合,集合也不是Map。因此,Map继承Collection毫无意义。如果Map继承Collection接口,那么元素去哪儿?Map包含key-value键值对,它提供抽取key或value列表集合的方法,但是它不适合"一组对象"规范