【面试】JavaEE基础

参考:https://github.com/Snailclimb/JavaGuide/blob/master/docs/java/J2EE基础知识.md

1、Servlet

参考:https://www.cnblogs.com/Rain1203/p/10919557.html

2、get和post请求的区别?

1)get请求用来从服务器上获取资源,post是用来向服务器提交数据的;

2)get将表单中数据按照name=value的形式,添加到action所指向的URL后面,并且两者使用“?”连接,而各个变量之间使用“&”连接;post是将表单中的数据放在HTTP协议的请求头或消息体中,传递到action所指向的URL;

3)get传输的数据要受到URL长度的限制(最大2048个字符),而post可以传输大量的数据,上传文件通常使用post方式;

4)使用get请求参数会显示在地址栏上,非敏感数据可以使用get方式,敏感数据应该使用post;

5)get使用MIME类型application/x-www-form-urlencoded的URL编码(也叫百分号编码)文本的格式传递参数,保证被传送的参数由遵循规范的文本组成,例如一个空格的编码是“%20”。

补充:get方式表单的典型应用是搜索引擎,get方式就是被设计为查询用的。

 

3、转发(Forward)和重定向(Redirect)的区别?

转发是服务器的行为,重定向是客户端的行为。

转发(Forward)通过RequestDispatcher对象的forward(HttpServletRequest request,HttpServletResponse response)方法实现的。

RequestDispatcher可以通过HttpServletRequest的getRequestDispatcher()方法获得。

request.getRequestDispatcher("login_success.jsp").forward(request,response);

重定向(Redirect)是利用服务器返回的状态码来实现的。客户端浏览器请求服务器的时候,服务器会返回一个状态码。服务器通过HttpServletResponse 的 setStatus(int status)方法设置状态码,如果服务器返回301或者302,则浏览器会跳转到新的网址重新获取资源。

1)从地址栏显示来说

forward是服务器请求资源,服务器直接访问目标URL把资源读取过来,返回给浏览器,浏览器并不知道服务器发送的资源从何而来,所以地址栏是不变的;

redirect是服务器根据逻辑,发送一个状态码,告诉浏览器去请求那个地址,所以地址栏显示的是新的URL;

2)从数据共享来说

forward转发页面和转发到的页面可以共享request里面的数据;

redirect不能共享数据;

3)从运用地方来说

forward一般用于用户登录的时候,根据角色转发到相应模块;

redirect一般用于用户注销登录时返回主页或跳转到其他网站等;

4)从效率来说

forward高;redirect低。

 

4、Servlet与线程安全?

Servlet不是线程安全的,多线程并发的读写会导致数据不同步的问题。解决的办法是尽量不要定义name属性,而是要把name变量分别定义在doGet()和doPost()方法内。虽然是以synchronized(name){} 语句块可以解决问题,但是会造成线程的等待,不是很科学的办法。注意,多线程的并发读写Servlet类属性会导致数据不同步。但是如果只是并发的读取属性而不写入,则不存在数据不同步的问题。因此,Servlet里的只读属性最好定义为final。

 

5、JSP中的四种作用域?

1)page代表与一个页面相关的对象和属性;

2)request代表与web客户端发出的一个请求相关的对象和属性。一个请求可能跨越多个页面,涉及多个web组件;需要在页面显示的临时数据可以置于此作用域;

3)session代表某个用户与服务器建立的一次会话相关的对象和属性。跟某个用户相关的数据应该放在用户自己的session中;

4)application代表与整个web应用程序相关的对象和属性,它实质上是跨越整个web应用程序,包括多个页面,请求和会话的一个全局作用域。

 

6、如何实现JSP或Servlet的单线程模式?

对于JSP页面,可以通过page指令进行设置。<%@page isThreadSafe="false'%>;

对于Servlet,可以让自定义的Servlet实现SingleThreadModel 标识接口;

说明:如果将JSP或Servlet设置成单线程工作模式,会导致每个请求创建一个Servlet实例,这种将导致严重的性能问题(服务器的内存压力很大,还会导致频繁的垃圾回收),所以通常情况下我们不会这么做。

 

7、实时会话跟踪的技术有哪些?

1)使用Cookie

向客户端发送Cookie

Cookie c =new Cookie("name","value"); //创建Cookie 
c.setMaxAge(60*60*24); //设置最大时效,此处设置的最大时效为一天
response.addCookie(c); //把Cookie放入到HTTP响应中

 从客户端读取Cookie

String name ="name"; 
Cookie[]cookies =request.getCookies(); 
if(cookies !=null){ 
   for(int i= 0;i<cookies.length;i++){ 
    Cookie cookie =cookies[i]; 
    if(name.equals(cookis.getName())) 
    //something is here. 
    //you can get the value 
    cookie.getValue(); 
       
   }
 }

优点:数据可以持久保存,不需要服务器资源,简单,基于文本的key-Value;

缺点:大小受到限制,用户可以禁用Cookie功能,有一定的安全风险。

2)URL重写

在URL中添加用户会话的信息作为请求参数,或者将唯一的会话ID添加到URL结尾以标识成一个会话;

优点:在Cookie被禁用时仍然可以使用;

缺点:必须对网站的URL进行编码,所有页面必须动态生成,不能用预先记录下来的URL进行访问;

3)隐藏的表单域

<input type="hidden" name ="session" value="..."/>

优点:Cookie被禁用时可以使用;

缺点:所有页面必须是表单提交之后的结果。

4)HttpSession

在所有会话跟踪技术中,HttpSession对象是最强大也是功能最多的。当一个用户第一次访问某个网站时会自动创建HttpSession,每个用户可以访问它自己的HttpSession。可以通过HttpServletRequest对象的getSession()方法获取HttpSession,通过HttpSession的setAttribute方法可以将一个值放到HttpSession中,通过调用HttpSession对象的getAttribute方法,同时传入属性名就可以获取保存在HttpSession中的对象。

与上面三种方式不同的是,HttpSession放在服务器的内存中,因此不要将过大的对象放在里面,即使目前的Servlet容器可以在内存将满时将HttpSession中的对象移到其他存储设备中,但这势必影响性能。添加到HttpSession中的值可以是任意Java对象,这个对象最好实现了Serializable接口,这样Servlet容器在必要的时候可以将其序列化到文件中,否则在序列化时容易出现异常。

 

8、Cookie和Session的区别?

Cookie和Session都是用来跟踪浏览器用户身份的会话方式,但是两者的应用场景不太一样。

Cookie一般用来保护用户信息,比如(1)我们在Cookie保存已经登录过的用户信息,下次访问网站的时候可以帮你把登录的信息给填了;

(2)一般的网站都会有保持登录,也就是说你下次再访问网站就不需要重新登录了,这是因为用户登录的时候我们存放了一个Token在Cookie中,下次登录的时候只需要根据Token值来查找用户即可(为了安全考虑,重新登录一般要将Token重写);

(3)登录一次网站后访问网站其他页面不需要重新登录。

Session的主要作用就是通过服务端记录用户状态。典型的场景是购物车,当你要添加商品到购物车的时候,系统不知道是哪个用户操作的,因为HTTP协议是无状态的。服务端给特定的用户创建特定的Session之后,就可以标识这个用户并且跟踪这个用户了。

Cookie数据保存在客户端(浏览器),Session保存在服务器端;

Session安全性更高,如果使用Cookie的一些敏感信息不要直接写入到Cookie中,最好能将Cookie信息加密,然后使用到的时候再去服务器端解密。

 

 

原文地址:https://www.cnblogs.com/Rain1203/p/11240000.html