java面试题六

51、 什么时候使用字节流、什么时候使用字符流,二者的区别

在程序中所有的数据都是以流的方式进行传输或保存的,程序需要数据的时候要使用输入流读取数据,而当程序需要将一些数据保存起来的时候,就要使用输出流完成。


InputStream 和OutputStream,两个是为
字节流设计的,主要用来处理字节或二进制对象,
Reader和Writer.两个是为
字符流(一个字符占两个字节)设计的,主要用来处理字符或字符串.
 
字符流处理的单元为2个字节的Unicode字符,操作字符、字符数组或字符串,
字节流处理单元为1个字节,操作字节和字节数组。
所以字符流是由
Java虚拟机将字节转化为2个字节的Unicode字符为单位的字符而成的,
所以它对多国语言支持性比较好!
如果是音频文件、图片、歌曲,就用字节流好点,
如果是关系到中文(文本)的,用字符流好点


所有文件的储存是都是字节(byte)的储存,在磁盘上保留的并不是文件的字符而是先把字符编码成字节,再储存这些字节到磁盘。在读取文件(特别是文本文件)时,也是一个字节一个字节地读取以形成字节序列
字节流可用于任何类型的对象,包括二进制对象,而字符流只能处理字符或者字符串;
字节流提供了处理任何类型的IO操作的功能,但它不能直接处理Unicode字符,而字符流就可以
字节流是最基本的,所有的InputStrem和OutputStream的子类都是,主要用在处理二进制数据,它是按字节来处理的 
但实际中很多的数据是文本,
又提出了字符流的概念,
它是按虚拟机的encode来处理,也就是要进行字符集的转化 
这两个之间通过InputStreamReader,OutputStreamWriter来关联,
实际上是通过byte[]和String来关联 
在实际开发中出现的汉字问题实际上都是在字符流和字节流之间转化不统一而造成的 

Reader类的read()方法返回类型为int :作为整数读取的字符(占两个字节共16位),范围在 0 到 65535 之间(0x00-0xffff),如果已到达流的末尾,则返回-1

inputStream的read()虽然也返回int,但由于此类是面向字节流的,一个字节占8个位,所以返回 0 到 255 范围内的 int 字节值。如果因为已经到达流末尾而没有可用的字节,则返回值-1。因此对于不能用0-255来表示的值就得用字符流来读取!比如说汉字.

字节流和字符流的主要区别是什么呢?

          一.字节流在操作时不会用到缓冲区(内存),是直接对文件本身进行操作的。而字符流在操作时使用了缓冲区,通过缓冲区再操作文件。

 

          二.在硬盘上的所有文件都是以字节形式存在的(图片,声音,视频),而字符值在内存中才会形成。

 

 

    上面两点能说明什么呢?

       针对第一点,

      我们知道,如果一个程序频繁对一个资源进行IO操作,效率会非常低。此时,通过缓冲区,先把需要操作的数据暂时放入内存中,以后直接从内存中读取数据,则可以避免多次的IO操作,提高效率

      针对第二点,

      真正存储和传输数据时都是以字节为单位的,字符只是存在与内存当中的,所以,字节流适用范围更为宽广

52、session和cookie的区别和联系,session的生命周期,多个服务部署时session管理

Session和Cookie的区别

对象

信息量大小

保存时间

应用范围

保存位置

Session

小量,简单的数据

用户活动时间+一段延迟时间(一般为20分钟)

单个用户

服务器端

Cookie

小量,简单的数据

可以根据需要设定

单个用户

客户端

1.1 Session对象 

浏览器访问服务器时,服务器会创建一个对象(该对象也称为session对象,该对象有一个唯一的id号与其对应)。然后
,服务器会将id号发送给浏览器(默认情况下,使用cookie机制发送)。当浏览器再次访问服务器时,会将id号发送过
来。服务器可以依据id号找到对应的session对象。通过这个session对象,来保存状态。 
1.1.1 session在不同环境下的不同含义 
  session,中文经常翻译为会话,其本来的含义是指有始有终的一系列动作/消息,比如打电话是从拿起电话拨号到挂
断电话这中间的一系列过程可以称之为一个session。 
然而当session一词与网络协议相关联时,它又往往隐含了“面向连接”和/或“保持状态”这样两个含义。 
  session在Web开发环境下的语义又有了新的扩展,它的含义是指一类用来在客户端与服务器端之间保持状态的解决
方案。有时候Session也用来指这种解决方案的存储结构。 
1.1.2 保存session id的几种方式 
A.保存session id的方式可以采用cookie,这样在交互过程中浏览器可以自动的按照规则把这个标识发送给服务器。 
如果客户端支持Cookie,Web Server在返回Response的时候,在Response的Header部分,加入一个“set-cookie: 
jsessionid=XXXX”header属性,把jsessionid放在Cookie里传到客户端。 
B.由于cookie可以被人为的禁止,必须有其它的机制以便在cookie被禁止时仍然能够把session id传递回服务器,经常
采用的一种技术叫做URL重写,就是把session id附加在URL路径的后面,附加的方式也有两种,一种是作为URL路径的附
加信息,另一种是作为查询字符串附加在URL后面。网络在整个交互过程中始终保持状态,就必须在每个客户端可能请求
的路径后面都包含这个session id。 
C.另一种技术叫做表单隐藏字段。就是服务器会自动修改表单,添加一个隐藏字段,以便在表单提交时能够把session 
id传递回服务器。 
1.1.3 URL重写有什么缺点 
   对所有的URL使用URL重写,包括超链接,form的action,和重定向的URL。每个引用你的站点的URL,以及那些返
回给用户的URL(即使通过间接手段,比如服务器重定向中的Location字段)都要添加额外的信息。 
   这意味着在你的站点上不能有任何静态的HTML页面(至少静态页面中不能有任何链接到站点动态页面的链接)。因
此,每个页面都必须使用servlet或JSP动态生成。即使所有的页面都动态生成,如果用户离开了会话并通过书签或链接
再次回来,会话的信息都会丢失,因为存储下来的链接含有错误的标识信息-该URL后面的SESSION ID已经过期了。 
1.1.4 使用隐藏的表单域有什么缺点 
仅当每个页面都是有表单提交而动态生成时,才能使用这种方法。单击常规的<A HREF..>超文本链接并不产生表单提交
,因此隐藏的表单域不能支持通常的会话跟踪,只能用于一系列特定的操作中,比如在线商店的结账过程。
1.1.5 session什么时候被创建 
一个常见的错误是以为session在有客户端访问时就被创建,然而事实是直到某server端程序(如Servlet)调用
HttpServletRequest.getSession(true)这样的语句时才会被创建。 
1.1.6 session何时被删除 
session在下列情况下被删除: 
A.程序调用HttpSession.invalidate() 
B.距离上一次收到客户端发送的session id时间间隔超过了session的最大有效时间 
C.服务器进程被停止 
再次注意关闭浏览器只会使存储在客户端浏览器内存中的session cookie失效,不会使服务器端的session对象失效。 
1.2 Cookie对象 
浏览器向服务器发送请求时,服务器会将少量的数据返回给浏览器(该数据以set-cookie消息头的形式返回给浏览器)
,浏览器会将这些数据存放到硬盘或者内存上。当浏览器下次再次访问服务器时,会将之前存放的数据发送给服务器(
以cookie消息头的形式发送给服务器)。通过这种方式,就可以记录浏览器与服务器之间交互的数据,也就是状态。 
1.2.1 会话cookie和持久cookie的区别 
如果不设置过期时间,则表示这个cookie生命周期为浏览器会话期间,只要关闭浏览器窗口,cookie就消失了。这种生
命期为浏览会话期的cookie被称为会话cookie。会话cookie一般不保存在硬盘上而是保存在内存里。 
  如果设置了过期时间,浏览器就会把cookie保存到硬盘上,关闭后再次打开浏览器,这些cookie依然有效直到超过
设定的过期时间。 
  存储在硬盘上的cookie可以在不同的浏览器进程间共享,比如两个IE窗口。而对于保存在内存的cookie,不同的浏
览器有不同的处理方式。 
2.Session和Cookie的关系 
这里用一个形象的比喻来解释session的工作方式。假设 
Web Server:是一个商场的存包处
HTTP Request:是一个顾客
Session:商场的存包处的柜子
Session ID:存包号码牌
Cookie:客户随身携带不离身的钱包
情况一:一个顾客(HTTP Request),第一次来到存包处(Web Server),管理员把顾客的物品存放在某一个柜子里面
(Session),然后把一个号码牌(Session ID)交给这个顾客,作为取包凭证。 
情况二:顾客(HTTP Request)下一次来的时候,就要把号码牌(Session ID)交给存包处(Web Server)的管理员。
管理员根据号码牌(Session ID)找到相应的柜子(Session),根据顾客(HTTP Request)的请求,存包处(Web 
Server)可以取出、更换、添加柜子(Session)中的物品,存包处(Web Server)也可以让顾客(HTTP Request)的号
码牌和号码牌对应的柜子(Session)失效。 
情况三:顾客(HTTP Request)的忘性很大,管理员在顾客回去的时候(HTTP Response)都要重新提醒顾客记住自己的
号码牌(Session ID)。这样,顾客(HTTP Request)下次来的时候,就又带着号码牌回来了。 
情况四:客户(HTTP Request)把拿到的号码牌(Session ID)放到随身携带不离身的钱包(Cookie)中。 
3.Session和Cookie的应用 
3.1 如何利用实现自动登录 
当用户在某个网站注册后,就会收到一个惟一用户ID的cookie。客户后来重新连接时,这个用户ID会自动返回,服务器
对它进行检查,确定它是否为注册用户且选择了自动登录,从而使用户务需给出明确的用户名和密码,就可以访问服务
器上的资源。 
3.2 如何根据用户的爱好定制站点 
网站可以使用cookie记录用户的意愿。对于简单的设置,网站可以直接将页面的设置存储在cookie中完成定制。然而对
于更复杂的定制,网站只需仅将一个惟一的标识符发送给用户,由服务器端的数据库存储每个标识符对应的页面设置。 
3.3 cookie的发送 
    1) 创建Cookie对象 
    2) 设置最大时效 
    3) 将Cookie放入到HTTP响应报头 
如果你创建了一个cookie,并将他发送到浏览器,默认情况下它是一个会话级别的cookie:存储在浏览器的内存中,用户
退出浏览器之后被删除。如果你希望浏览器将该cookie存储在磁盘上,则需要使用maxAge,并给出一个以秒为单位的时
间。将最大时效设为0则是命令浏览器删除该cookie。 
发送cookie需要使用HttpServletResponse的addCookie方法,将cookie插入到一个Set-Cookie HTTP请求报头中。由于
这个方法并不修改任何之前指定的Set-Cookie报头,而是创建新的报头,因此我们将这个方法称为是addCookie,而非
setCookie。同样要记住响应报头必须在任何文档内容发送到客户端之前设置。 
Java代码  收藏代码
Cookie cookie = new Cookie("duanqftest", "22222");   
cookie.setDomain("172.20.40.73");    
cookie.setMaxAge(60000);    
cookie.setPath("/");    
response.addCookie(cookie);   
javax.servlet.http.Cookie[] diskCookies = request.getCookies();    
response.sendRedirect("ReadCookie");  
3.4 cookie的读取 
1) 调用request.getCookie 
要获取有浏览器发送来的cookie,需要调用HttpServletRequest的getCookies方法,这个调用返回Cookie对象的数组,
对应由HTTP请求中Cookie报头输入的值。 
2) 对数组进行循环,调用每个cookie的getName方法,直到找到感兴趣的cookie为止 
cookie与你的主机(域)相关,而非你的servlet或JSP页面。因而,尽管你的servlet可能只发送了单个cookie,你也可能
会得到许多不相关的cookie。 
Java代码  收藏代码
String cookieName = “userID”;  
Cookie cookies[] = request.getCookies();  
if (cookies!=null)  
{  
    for(int i=0;i<cookies.length;i++)  
    {  
        Cookie cookie = cookies[i];  
        if (cookieName.equals(cookie.getName()))  
            doSomethingWith(cookie.getValue()); 
    }  
}  
3.5 如何使用cookie检测初访者 
    A.调用HttpServletRequest.getCookies()获取Cookie数组 
    B.在循环中检索指定名字的cookie是否存在以及对应的值是否正确 
    C.如果是则退出循环并设置区别标识 
    D.根据区别标识判断用户是否为初访者从而进行不同的操作 
3.6 使用cookie检测初访者的常见错误 
不能仅仅因为cookie数组中不存在在特定的数据项就认为用户是个初访者。如果cookie数组为null,客户可能是一个初
访者,也可能是由于用户将cookie删除或禁用造成的结果。 
但是,如果数组非null,也不过是显示客户曾经到过你的网站或域,并不能说明他们曾经访问过你的servlet。其它
servlet、JSP页面以及非Java Web应用都可以设置cookie,依据路径的设置,其中的任何cookie都有可能返回给用户的
浏览器。 
正确的做法是判断cookie数组是否为空且是否存在指定的Cookie对象且值正确。 
3.7 使用cookie属性的注意问题 
属性是从服务器发送到浏览器的报头的一部分;但它们不属于由浏览器返回给服务器的报头。  
  因此除了名称和值之外,cookie属性只适用于从服务器输出到客户端的cookie;服务器端来自于浏览器的cookie并
没有设置这些属性。  
  因而不要期望通过request.getCookies得到的cookie中可以使用这个属性。这意味着,你不能仅仅通过设置cookie
的最大时效,发出它,在随后的输入数组中查找适当的cookie,读取它的值,修改它并将它存回Cookie,从而实现不断改
变的cookie值。 
3.8 如何使用cookie记录各个用户的访问计数 
    1) 获取cookie数组中专门用于统计用户访问次数的cookie的值 
    2) 将值转换成int型 
    3) 将值加1并用原来的名称重新创建一个Cookie对象 
    4) 重新设置最大时效 
    5) 将新的cookie输出 
3.9 会话跟踪的基本步骤 
    1) 访问与当前请求相关的会话对象 
    2) 查找与会话相关的信息 
    3) 存储会话信息 
    4) 废弃会话数据 
3.10 getSession()/getSession(true)、getSession(false)的区别 
getSession()/getSession(true):当session存在时返回该session,否则新建一个session并返回该对象。 
getSession(false):当session存在时返回该session,否则不会新建session,返回null

 

53、关于Servlet对象的线程安全问题:

      

              1、什么时候需要考虑线程安全问题?

                     *多线程并发的环境下

  • 0
    点赞
  • 4
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值