牛客java专项错误集锦

Java.exe是java虚拟机

javadoc.exe用来制作java文档

jdb.exe是java的调试器

Javaprof.exe是剖析工具

来自 <http://www.nowcoder.com/test/question/done?tid=4164892&qid=2282>

 

算法定义:

算法包括0个或多个输入,1个或多个输出,中间有穷个处理过程。

来自 <http://www.nowcoder.com/test/question/done?tid=4164892&qid=15550#summary>

 

方法重载(overload

1.必须是同一个类

2方法名(也可以叫函数)一样

3参数类型不一样或参数数量不一样

方法的重写(override两同两小一大原则:

方法名相同,参数类型相同

子类返回类型小于等于父类方法返回类型,

子类抛出异常小于等于父类方法抛出异常,

子类访问权限大于等于父类方法访问权限。

来自 <http://www.nowcoder.com/test/question/done?tid=4164892&qid=14993#summary>

 

优化Hibernate所鼓励的7大措施:

1.尽量使用many-to-one,避免使用单向one-to-many

2.灵活使用单向one-to-many

3.不用一对一,使用多对一代替一对一

4.配置对象缓存,不使用集合缓存

5.一对多使用Bag 多对一使用Set

6.继承使用显示多态 HQL:from object polymorphism=”exlicit” 避免查处所有对象

7.消除大表,使用二级缓存

来自 <http://www.nowcoder.com/test/question/done?tid=4164892&qid=15209#summary>

 

Transient:

java语言的关键字,变量修饰符,如果用transient声明一个实例变量,当对象存储时,它的值不需要维持。换句话来说就是,用transient关键字标记的成员变量不参与序列化过程。

使用ObjectOutputStream和ObjectInputStream可以将对象进行传输.

声明为static和transient类型的成员数据不能被串行化。因为static代表类的状态, transient代表对象的临时数据。

来自 <http://www.nowcoder.com/profile/442458/wrongset/29367384?page=1&offset=0&tags=>

 

“c.getDeclaredMethods”的作用:

 

public Method[] getMethods()返回某个类的所有公用(public)方法包括其继承类的公用方法,当然也包括它所实现接口的方法。

public Method[] getDeclaredMethods()对象表示的类或接口声明的所有方法, 包括公共、保护、默认(包)访问和私有方法,但不包括继承的方法。当然也包括它所实现接口的方法。

来自 <http://www.nowcoder.com/questionTerminal/f25d8986e8244d74a5666dab2c6872a8>

 

线程内顺序执行,线程间交叉执行。

来自 <http://www.nowcoder.com/questionTerminal/25deb8d21e7d442e86c90302d6e03133>

 

构造方法每次都是构造出新的对象,不存在多个线程同时读写同一对象中的属性的问题,所以不需要同步 。

如果父类中的某个方法使用了 synchronized关键字,而子类中也覆盖了这个方法,默认情况下子类中的这个方法并不是同步的,必须显示的在子类的这个方法中加上 synchronized关键字才可。当然,也可以在子类中调用父类中相应的方法,这样虽然子类中的方法并不是同步的,但子类调用了父类中的同步方法,也就相当子类方法也同步了。详见:http://blog.csdn.net/welcome000yy/article/details/8941644

接口里面的变量为常量,其实际是 public static final ;接口里面的方法为抽象方法,其实际是public abstract。

来自 <http://www.nowcoder.com/test/question/done?tid=4167605&qid=14929#summary>

 

原子性操作,不需要同步。

来自 <http://www.nowcoder.com/test/question/done?tid=4167605&qid=36395#summary>

 

HttpServlet是GenericServlet的子类。

GenericServlet是个抽象类,必须给出子类才能实例化。它给 出了设计servlet的一些骨架,定义了servlet生命周期,还有一些得到名字、配置、初始化参数的方法,其设计的是和应用层协议无关的,也就是说 你有可能用非http协议实现它。

HttpServlet是子类,当然就具有GenericServlet的一切特性,还添加了doGet, doPost, doDelete, doPut, doTrace等方法对应处理http协议里的命令的请求响应过程。

一般没有特殊需要,自己写的Servlet都扩展HttpServlet 。

来自 <http://www.nowcoder.com/test/question/done?tid=4167605&qid=15035#summary>

JSP内置对象和属性列举如下:

1.request对象

客户端的请求信息被封装在request对象中,通过它才能了解到客户的需求,然后做出响应。它是HttpServletRequest类的实例。

2.response对象

response对象包含了响应客户请求的有关信息,但在JSP中很少直接用到它。它是HttpServletResponse类的实例。

3.session对象

session对象指的是客户端与服务器的一次会话,从客户连到服务器的一个WebApplication开始,直到客户端与服务器断开连接为止。它是HttpSession类的实例.

4.out对象

out对象是JspWriter类的实例,是向客户端输出内容常用的对象

5.page对象

page对象就是指向当前JSP页面本身,有点象类中的this指针,它是java.lang.Object类的实例

6.application对象

application对象实现了用户间数据的共享,可存放全局变量。它开始于服务器的启动,直到服务器的关闭,在此期间,此对象将一直存在;这样在用户的前后连接或不同用户之间的连接中,可以对此对象的同一属性进行操作;在任何地方对此对象属性的操作,都将影响到其他用户对此的访问。服务器的启动和关闭决定了application对象的生命。它是ServletContext类的实例。application对象是共享的,多个用户共享一个,以此实现数据共享和通信

7.exception对象

exception对象是一个例外对象,当一个页面在运行过程中发生了例外,就产生这个对象。如果一个JSP页面要应用此对象,就必须把isErrorPage设为true,否则无法编译。他实际上是java.lang.Throwable的对象

8.pageContext对象

pageContext对象提供了对JSP页面内所有的对象及名字空间的访问,也就是说他可以访问到本页所在的SESSION,也可以取本页面所在的application的某一属性值,他相当于页面中所有功能的集大成者,它的本 类名也叫pageContext。

9.config对象

config对象是在一个Servlet初始化时,JSP引擎向它传递信息用的,此信息包括Servlet初始化时所要用到的参数(通过属性名和属性值构成)以及服务器的有关信息(通过传递一个ServletContext对象)

来自 <http://www.nowcoder.com/test/question/done?tid=4175151&qid=14780#summary>

 

linkedList、ArrayList都不是线程安全的,Vector是线程安全的,但是效率很低,现在很少用

Hashtable和Hasnmap功能差不多,但Hashtables是线程安全的。集合中线程安全的类有:vector,stack,hashtable,enumeration,除此之外均是非线程安全的类与接口

来自 <http://www.nowcoder.com/test/question/done?tid=4175151&qid=44625#summary>

 

内部类的使用

public class Enclosingone {

//非静态内部类

public class InsideOne {}

//静态内部类

public static class InsideTwo{}

}

 

class Mytest02{

public static void main(String args []){

Enclosingone.InsideOne obj1 = new Enclosingone().new InsideOne();//非静态内部类对象

Enclosingone.InsideTwo obj2 = new Enclosingone.InsideTwo();//静态内部类对象

}

}

来自 <http://www.nowcoder.com/test/question/done?tid=4175630&qid=7673#summary>

 

枚举类 所有的枚举值都是类静态常量,在初始化时会对所有的枚举值对象进行第一次初始化。

来自 <http://www.nowcoder.com/test/question/done?tid=4175630&qid=7688#summary>

 

依赖注入和控制反转是同一概念:

依赖注入和控制反转是对同一件事情的不同描述,从某个方面讲,就是它们描述的角度不同。依赖注入是从应用程序的角度在描述,可以把依赖注入描述完整点:应用程序依赖容器创建并注入它所需要的外部资源;而控制反转是从容器的角度在描述,描述完整点:容器控制应用程序,由容器反向的向应用程序注入应用程序所需要的外部资源。

来自 <http://www.nowcoder.com/test/question/done?tid=4175630&qid=15547#summary>

 

加载驱动方法

      1. Class.forName(“com.microsoft.sqlserver.jdbc.SQLServerDriver”);
      2. DriverManager.registerDriver(new com.mysql.jdbc.Driver());
      3. System.setProperty(“jdbc.drivers”, “com.mysql.jdbc.Driver”);

而 DriverManager.getConnection方法返回一个Connection对象,这是加载驱动之后才能进行的

来自 <http://www.nowcoder.com/test/question/done?tid=4175630&qid=15247#summary>

 

关于并发:

CopyOnWriteArrayList适用于写少读多的并发场景

ReadWriteLock即为读写锁,他要求写与写之间互斥,读与写之间互斥,读与读之间可以并发执行。在读多写少的情况下可以提高效率

ConcurrentHashMap是同步的HashMap,读不加锁,写加锁

volatile只保证多线程操作的可见性,不保证原子性(i++)

对于volatile修饰的变量,jvm虚拟机只是保证从主内存加载到线程工作内存的值是最新的,同时线程工作内存中的操作并不是原子性的。所以在一个线程对该变量进行操作的同时,其他的线程有可能也在对该变量进行操作。

来自 <http://www.nowcoder.com/test/question/done?tid=4175630&qid=16023#summary>

 

所谓 volatile的措施,就是

  1. 每次从内存中取值,不从缓存中什么的拿值。这就保证了用 volatile修饰的共享变量,每次的更新对于其他线程都是可见的。
  2. volatile保证了其他线程的立即可见性,就没有保证原子性。

3.由于有些时候对 volatile的操作,不会被保存,说明不会造成阻塞。不可用于多线程环境下的计数器。

来自 <http://www.nowcoder.com/test/question/done?tid=4185531&qid=25776#summary>

 

 

 

 

异常是指程序运行时(非编译)所发生的非正常情况或错误,当程序违反了语音规则,jvm就会将出现的错误表示一个异常抛出。

异常也是java 的对象,定义了基类 java。lang。throwable作为异常父类。 这些异常类又包括error和exception。两大类

error类异常主要是运行时逻辑错误导致,一个正确程序中是不应该出现error的。当出现error一般jvm会终止。

exception表示可恢复异常,包括检查异常和运行时异常。 检查异常是最常见异常比如 io异常sql异常,都发生在编译阶段。这类通过try、catch捕捉

而运行时异常,编译器没有强制对其进行捕捉和处理。一般都会把异常向上抛出,直到遇到处理代码位置,若没有处理块就会抛到最上层,多线程用thread。run()抛出,单线程用main()抛出。常见的运行异常包括 空指针异常 类型转换异常 数组月结异常 数组存储异常 缓冲区溢出异常 算术异常等,

来自 <http://www.nowcoder.com/test/question/done?tid=4175630&qid=14759#summary>

 

都是Throwable的子类: 

1.Exception(异常) :是程序本身可以处理的异常。

2.Error(错误): 是程序无法处理的错误。这些错误表示故障发生于虚拟机自身、或者发生在虚拟机试图执行应用时,一般不需要程序处理。

3.检查异常(编译器要求必须处置的异常) :  除了Error,RuntimeException及其子类以外,其他的Exception类及其子类都属于可查异常。这种异常的特点是Java编译器会检查它,也就是说,当程序中可能出现这类异常,要么用try-catch语句捕获它,要么用throws子句声明抛出它,否则编译不会通过。

4.非检查异常(编译器不要求处置的异常): 包括运行时异常(RuntimeException与其子类)和错误(Error)。

checked exceptions: 通常是从一个可以恢复的程序中抛出来的,并且最好能够从这种异常中使用程序恢复。比如FileNotFoundException, ParseException等。

unchecked exceptions: 通常是如果一切正常的话本不该发生的异常,但是的确发生了。比如ArrayIndexOutOfBoundException, ClassCastException等

来自 <http://www.nowcoder.com/questionTerminal/9e4e6d1f6bc2456aaaaa2dff4c94f9ab>

 

题目:

Integer i01=59;

int i02=59;

Integer i03=Integer.valueOf(59);

Integer i04=new Integer(59);

 

解析:

Integer i01 = 59. 直接赋值数字,java会自动装箱,自动调用Integer.valueOf(59).

Integer i03 = Integer.valueOf(59).  Integer.valueOf(int i)会返回一个Integer对象,当i在-128~127之间时,会返回缓存中已创建的Integer对象。

Integer i04 = new Integer(59) 返回一个新的对象。

所以这道题中,59在-128~127之间,所以前三条语句返回的是同一个对象(在缓存区已创建的对象),而i04使用new新创建了一个新的对象,所以i04与前面三个对象都不一样。

而i02 = i04 是因为Integer会自动拆箱为int类型再比较,所以为true

来自 <http://www.nowcoder.com/test/question/done?tid=4175630&qid=36316#summary>

suspend() 和 resume() 方法:两个方法配套使用,suspend()使得线程进入阻塞状态,并且不会自动恢复,必须其对应的 resume() 被调用,才能使得线程重新进入可执行状态

wait与notify(notifyAll)一起使用

sleep会让线程暂时不执行

来自 <http://www.nowcoder.com/test/question/done?tid=4176913&qid=15542#summary>

 

面向对象的五个基本原则:

单一职责原则(Single-Resposibility Principle):一个类,最好只做一件事,只有一个引起它的变化。单一职责原则可以看做是低耦合、高内聚在面向对象原则上的引申,将职责定义为引起变化的原因,以提高内聚性来减少引起变化的原因。

开放封闭原则(Open-Closed principle):软件实体应该是可扩展的,而不可修改的。也就是,对扩展开放,对修改封闭的。

里氏替换原则(Liskov-Substituion Principle):子类必须能够替换其基类。这一思想体现为对继承机制的约束规范,只有子类能够替换基类时,才能保证系统在运行期内识别子类,这是保证继承复用的基础。

依赖倒置原则(Dependecy-Inversion Principle):依赖于抽象。具体而言就是高层模块不依赖于底层模块,二者都同依赖于抽象;抽象不依赖于具体,具体依赖于抽象。

接口隔离原则(Interface-Segregation Principle):使用多个小的专门的接口,而不要使用一个大的总接口

来自 <http://www.nowcoder.com/test/question/done?tid=4176913&qid=14362#summary>

 

floor: 求小于参数的最大整数。返回double类型—–n. 地板,地面

例如:Math.floor(-4.2) = -5.0

———————————————————–

ceil:   求大于参数的最小整数。返回double类型—–vt. 装天花板;

例如:Math.ceil(5.6) = 6.0

———————————————————–

round: 对小数进行四舍五入后的结果。返回int类型

例如:Math.round(-4.6) = -5

来自 <http://www.nowcoder.com/test/question/done?tid=4176913&qid=7137#summary>

 

一般用system.in创建InputStream对象,表示从标准输入中获取数据,用system.out创建OutputStream对象,表示输出到标准输出设备中。

来自 <http://www.nowcoder.com/test/question/done?tid=4176913&qid=15126#summary>

 

static成员变量是在类加载的时候生成的

static成员函数既可以通过类名直接调用,也可以通过对象名进行调用

虚函数是C++中的,虚函数不可能是static的

static成员函数可以访问static成员变量

 

而java中抽象方法中不能用private,static, synchronized,native等修饰词修饰。

来自 <http://www.nowcoder.com/test/question/done?tid=4179953&qid=4015#summary>

 

ThreadLocal可以给一个初始值,而每个线程都会获得这个初始化值的一个副本,这样才能保证不同的线程都有一份拷贝。ThreadLocal

不是用于解决共享变量的问题的,不是为了协调线程同步而存在,而是为了方便每个线程处理自己的状态而引入的一个机制.

来自 <http://www.nowcoder.com/test/question/done?tid=4179953&qid=15262#summary>

 

java关键字

gotoconst是保留字也是关键字。

1,Java 关键字列表 (依字母排序 共50组):

abstract, assert, boolean, break, byte, case, catch, char, class, const(保留关键字), continue, default, do, double, else, enum,

extends, final, finally, float, for, goto(保留关键字), if, implements, import, instanceof, int, interface, long, native, new, package,

private, protected, public, return, short, static, strictfp, super, switch, synchronized, this, throw, throws, transient, try, void, volatile, while

2,保留字列表 (依字母排序 共14组),Java保留字是指现有Java版本尚未使用,但以后版本可能会作为关键字使用:

byValue, cast, false, future, generic, inner, operator, outer, rest, true, var, goto (保留关键字) , const (保留关键字) , null

来自 <http://www.nowcoder.com/test/question/done?tid=4180695&qid=14973#summary>

 

具体请参照:

<http://download.oracle.com/javase/tutorial/java/nutsandbolts/_keywords.html>

Java Language Keywords

Here is a list of keywords in the Java programming language. You cannot use any of the following

as identifiers in your programs. The keywords const and goto are reserved, even though they are

not currently used.  true, false, and  null might seem like keywords, but they are actually literals;

you cannot use them as identifiers in your programs.

java中true ,false , null在java中不是关键字,也不是保留字,它们只是显式常量值,但是你在程序中不能使用它们作为标识符。

其中const和goto是java的保留字。java中所有的关键字都是小写的,还有要注意true,false,null, friendly,sizeof不是java的关键字,但是你

不能把它们作为java标识符用。

来自 <http://www.nowcoder.com/test/question/done?tid=4239064&qid=7681#summary>

 

JUnit是一个Java语言的单元测试框架,有程序员自测,就是所谓的白盒测试,主要四个方向 1、用于测试期望结果的断言(Assertion)

2、用于共享共同测试数据的测试工具  3、用于方便的组织和运行测试的测试套件  4、图形和文本的测试运行器

来自 <http://www.nowcoder.com/test/question/done?tid=4180695&qid=36743#summary>

 

关于forward和redirect

1.从地址栏显示来说
forward是服务器请求资源,服务器直接访问目标地址的URL,把那个URL的响应内容读取过来,然后把这些内容再发给浏览器.浏览器根本不知道

服务器发送的内容从哪里来的,所以它的地址栏还是原来的地址.
redirect是服务端根据逻辑,发送一个状态码,告诉浏览器重新去请求那个地址.所以地址栏显示的是新的URL.
2.从数据共享来说
forward:转发页面和转发到的页面可以共享request里面的数据.
redirect:不能共享数据.
3.从运用地方来说
forward:一般用于用户登陆的时候,根据角色转发到相应的模块.
redirect:一般用于用户注销登陆时返回主页面和跳转到其它的网站等.
4.从效率来说
forward:高.
redirect:低.
本质区别

解释一

一句话,转发是服务器行为,重定向是客户端行为。为什么这样说呢,这就要看两个动作的工作流程:
转发过程:客户浏览器发送http请求—-》web服务器接受此请求–》调用内部的一个方法在容器内部完成请求处理和转发动作—-》将目标资源 发送给客户;在这里,转发的路径必须是同一个web容器下的url,其不能转向到其他的web路径上去,中间传递的是自己的容器内的request。在客 户浏览器路径栏显示的仍然是其第一次访问的路径,也就是说客户是感觉不到服务器做了转发的。转发行为是浏览器只做了一次访问请求。

redirect重定向过程:客户浏览器发送http请求—-》web服务器接受后发送302状态码响应及对应新的location给客户浏览器–》客户浏览器发现 是302响应,则自动再发送一个新的http请求,请求url是新的location地址—-》服务器根据此请求寻找资源并发送给客户。在这里 location可以重定向到任意URL,既然是浏览器重新发出了请求,则就没有什么request传递的概念了。在客户浏览器路径栏显示的是其重定向的 路径,客户可以观察到地址的变化的。重定向行为是浏览器做了至少两次的访问请求的。

解释二
重定向,其实是两次request, 第一次,客户端request A,服务器响应,并response回来,告诉浏览器,你应该去B。这个时候IE可以看到地址变了,而且历史的回退按钮也亮了。重定向可以访问自己web应用以外的资源。在重定向的过程中,传输的信息会被丢失。

解释三
假设你去办理某个执照,
重定向:你先去了A局,A局的人说:“这个事情不归我们管,去B局”,然后,你就从A退了出来,自己乘车去了B局。
转发:你先去了A局,A局看了以后,知道这个事情其实应该B局来管,但是他没有把你退回来,而是让你坐一会儿,自己到后面办公室联系了B的人,让他们办好后,送了过来。

来自 <http://www.nowcoder.com/questionTerminal/e14e58a3d78346be9540a3fbefd62ee3>

 

jdk的一些包和基本功能:

java.awt: 包含构成抽象窗口工具集的多个类,用来构建和管理应用程序的图形用户界面

java.lang: 提供java编成语言的程序设计的基础类

java.io:  包含提供多种输出输入功能的类,

java.net:  包含执行与网络有关的类,如URL,SCOKET,SEVERSOCKET,

java.applet: 包含java小应用程序的类

java.util:  包含一些实用性的类

来自 <http://www.nowcoder.com/test/question/done?tid=4181080&qid=14989#summary>

 

静态块:用static申明,JVM加载类时执行,仅执行一次

构造块:类中直接用{}定义,每一次创建对象时执行

执行顺序优先级:静态块>main()>构造块>构造方法

静态变量和静态代码块的执行顺序就是代码前后的顺序 ★

来自 <http://www.nowcoder.com/test/question/done?tid=4181080&qid=14700#summary>

 

AWT和Swing之间的区别:

1)AWT 是基于本地方法的C/C++程序,其运行速度比较快;Swing是基于AWT的Java程序,其运行速度比较慢。

2)AWT的控件在不同的平台可能表现不同,而Swing在所有平台表现一致。

在实际应用中,应该使用AWT还是Swing取决于应用程序所部署的平台类型。例如:

1)对于一个嵌入式应用,目标平台的硬件资源往往非常有限,而应用程序的运行速度又是项目中至关重要的因素。在这种矛盾的情况下,简单而高效的AWT当然成了嵌入式Java的第一选择。

2)在普通的基于PC或者是工作站的标准Java应用中,硬件资源对应用程序所造成的限制往往不是项目中的关键因素。所以在标准版的Java中则提倡使用Swing, 也就是通过牺牲速度来实现应用程序的功能。

来自 <http://www.nowcoder.com/test/question/done?tid=4181080&qid=15095#summary>

 

超文本传输协议(HTTP)的统一资源定位符将从因特网获取信息的五个基本元素包括在一个简单的地址中:

      1. 传送协议。
      2. 服务器。
      3. 端口号。(以数字方式表示,若为HTTP的默认值“:80”可省略)
      4. 路径。(以“/”字符区别路径中的每一个目录名称)
      5. 查询。(GET模式的窗体参数,以“?”字符为起点,每个参数以“&”隔开,再以“=”分开参数名称与数据,通常以UTF8的URL编码,避开字符冲突的问题)

典型的统一资源定位符看上去是这样的:

(带方括号[]的为可选项):

protocol :// hostname[:port] / path / [;parameters][?query]#fragment

来自 <http://www.nowcoder.com/test/question/done?tid=4185207&qid=15128#summary>

 

反射是通过一个名为Class的特殊类,用Class.forName(“className”);得到类的字节码对象,然后用newInstance()方法在虚拟机内部构造这个对象(针对无参构造函数)。

也就是说反射机制(的功能)让我们可以先拿到java类对应的字节码对象,然后动态的进行任何可能的操作,

包括

      1. 在运行时判断任意一个对象所属的类
      2. 在运行时构造任意一个类的对象
      3. 在运行时判断任意一个类所具有的成员变量和方法
      4. 在运行时调用任意一个对象的方法

这些都是反射的功能。

使用反射的主要作用是方便程序的扩展。

来自 <http://www.nowcoder.com/test/question/done?tid=4185207&qid=15427#summary>

 

根据操作系统中的定义:死锁是指在一组进程中的各个进程均占有不会释放的资源,但因互相申请被其他进程所站用不会释放的资源而处于的一种永久等待状态。(死锁强调阻塞进程 + 相互等待)

死锁的四个必要条件:

1互斥条件(Mutual exclusion):资源不能被共享,只能由一个进程使用。

2请求与保持条件(Hold and wait):已经得到资源的进程可以再次申请新的资源。

3非剥夺条件(No pre-emption):已经分配的资源不能从相应的进程中被强制地剥夺。

4循环等待条件(Circular wait):系统中若干进程组成环路,该环路中每个进程都在等待相邻进程正占用的资源。

来自 <http://www.nowcoder.com/test/question/done?tid=4185531&qid=15004#summary>

 

java中可以有多个重载的main方法,只有public static void main(String[] args){}是函数入口

来自 <http://www.nowcoder.com/test/question/done?tid=4185531&qid=15530#summary>

 

Struts工作原理

MVC即Model-View-Controller的缩写,是一种常用的设计模式。MVC   减弱了业务逻辑接口和数据接口之间的耦合,以及让视图层更富于变化。

Struts   是MVC的一种实现,它将   Servlet和   JSP   标记(属于   J2EE   规范)用作实现的一部分。Struts继承了MVC的各项特性,并根据J2EE的特点,做了相应的变化与扩展。

控 制:有一个XML文件Struts-config.xml,与之相关联的是Controller,在Struts中,承担MVC中Controller角 色的是一个Servlet,叫ActionServlet。ActionServlet是一个通用的控制组件。这个控制组件提供了处理所有发送到 Struts的HTTP请求的入口点。它截取和分发这些请求到相应的动作类(这些动作类都是Action类的子类)。另外控制组件也负责用相应的请求参数 填充   Action   From(通常称之为FromBean),并传给动作类(通常称之为ActionBean)。动作类实现核心商业逻辑,它可以访问java   bean   或调用EJB。最后动作类把控制权传给后续的JSP   文件,后者生成视图。所有这些控制逻辑利用Struts-config.xml文件来配置。

视图:主要由JSP生成页面完成视图,Struts提供丰富的JSP   标签库:   Html,Bean,Logic,Template等,这有利于分开表现逻辑和程序逻辑。

模 型:模型以一个或多个java   bean的形式存在。这些bean分为三类:Action   Form、Action、JavaBean   or   EJB。Action   Form通常称之为FormBean,封装了来自于Client的用户请求信息,如表单信息。Action通常称之为ActionBean,获取从 ActionSevlet传来的FormBean,取出FormBean中的相关信息,并做出相关的处理,一般是调用Java   Bean或EJB等。

流程:在Struts中,用户的请求一般以*.do作为请求服务名,所有的*.do请求均被指向 ActionSevlet,ActionSevlet根据Struts-config.xml中的配置信息,将用户请求封装成一个指定名称的 FormBean,并将此FormBean传至指定名称的ActionBean,由ActionBean完成相应的业务操作,如文件操作,数据库操作等。 每一个*.do均有对应的FormBean名称和ActionBean名称,这些在Struts-config.xml中配置。

核心:Struts的核心是ActionSevlet,ActionSevlet的核心是Struts-config.xml。

 

MVC 模式: web应用程序启动时就会加载并初始化ActionServler。用户提交表单时,一个配置好的ActionForm对象被创建,并被填入表单相应的数 据,ActionServler根据Struts-config.xml文件配置好的设置决定是否需要表单验证,如果需要就调用ActionForm的 Validate()验证后选择将请求发送到哪个Action,如果Action不存在,ActionServlet会先创建这个对象,然后调用 Action的execute()方法。Execute()从ActionForm对象中获取数据,完成业务逻辑,返回一个ActionForward对 象,ActionServlet再把客户请求转发给ActionForward对象指定的jsp组件,ActionForward对象指定的jsp生成动 态的网页,返回给客户。

来自 <http://www.nowcoder.com/questionTerminal/bbfa971aa43d4500b16ce57e2226fec6>

 

java中有两种方式实现线程:

1.class A继承Thread,并重写run方法,new A().start(),就执行了线程

2.class A实现Runnable,实现run方法,new Thread(new A()).start()

来自 <http://www.nowcoder.com/test/question/done?tid=4185531&qid=7674#summary>

 

如果希望监听TCP端口9000,应该怎样创建socket?

答案:new ServerSocket(9000);

 

解释:

ServerSocket  (int port)

创建一个serversocket 绑定在特定的端口

Socket(InetAddress address, int port)

创建一个socket流,连接到特定的端口和ip地址

来自 <http://www.nowcoder.com/test/question/done?tid=4185531&qid=26140#summary>

 

bootstrap classloader -引导(也称为原始)类加载器,它负责加载Java的核心类。 extension classloader -扩展类加载器,它负责加载JRE的扩展目录(JAVA_HOME/jre/lib/ext或者由java.ext.dirs系统属性指定的)中JAR的类包。 system classloader -系统(也称为应用)类加载器,它负责在JVM被启动时,加载来自在命令java中的-classpath或者java.class.path系统属性
或者 CLASSPATH*作系统属性所指定的JAR类包和类路径。

来自 <http://www.nowcoder.com/test/question/done?tid=4186741&qid=14760#summary>

 

终止线程:抛出一个异常时,该线程就终止了。√

而当一个优先级高的线程进入就绪状态时,它只是有较高的概率能够抢到CPU的执行权,不是一定就能抢到执行权。

或者当创建一个新的线程时,该线程也加入到了抢占cpu执行权的队伍中,但是是否能抢到,并不清楚。

当前线程调用sleep()方法或者wait()方法时,只是暂时停止了该线程的运行,不是终止线程,注意题目说的是“终止”,就是完全停止。

来自 <http://www.nowcoder.com/test/question/done?tid=4186741&qid=25712#summary>

 

HashMap不能保证元素的顺序,HashMap能够将键设为null,也可以将值设为null,与之对应的是Hashtable,(注意大小写:不是HashTable),Hashtable不能将键和值设为null,否则运行时会报空指针异常错误;

HashMap线程不安全,Hashtable线程安全

来自 <http://www.nowcoder.com/test/question/done?tid=4186741&qid=22476#summary>

 

-Xmx10240m -Xms10240m -Xmn5120m -XXSurvivorRatio=3

-Xmx:最大堆大小

-Xms:初始堆大小

-Xmn:年轻代大小

-XXSurvivorRatio:年轻代中Eden区与Survivor区的大小比值

年轻代5120m, Eden:Survivor=3,Survivor区大小=1024m(Survivor区有两个,即将年轻代分为5份,每个Survivor区占一份),总大小为2048m。

-Xms初始堆大小即最小内存值为10240m

 

-Xms -Xmx分别设置对的最小值和最大值,如果要设置成对的大小可变,那么可以将最大值和最小值设置成不一样,如果要将堆大小固定,那么只需将最大值和最小值设置成一样的就行。

jvm中分为堆和方法区

堆又进一步分为新生代和老年代

方法区为永久代

堆中区分的新生代和老年代是为了垃圾回收,新生代中的对象存活期一般不长,而老年代中的对象存活期较长,所以当垃圾回收器回收内存时,新生代中垃圾回收效果较好,会回收大量的内存,而老年代中回收效果较差,内存回收不会太多。

基于以上特性,新生代中一般采用复制算法,因为存活下来的对象是少数,所需要复制的对象少,而老年代对象存活多,不适合采用复制算法,一般是标记整理和标记清除算法。

因为复制算法需要留出一块单独的内存空间来以备垃圾回收时复制对象使用,所以将新生代分为eden区和两个survivor区,每次使用eden和一个survivor区,另一个survivor作为备用的对象复制内存区。

来自 <http://www.nowcoder.com/test/question/done?tid=4157037&qid=16021#summary>

 

List,Set,Map在java.util包下都是接口

List有两个实现类:ArrayList和LinkedList

Set有两个实现类:HashSet和LinkedHashSet

AbstractSet实现了Set

来自 <http://www.nowcoder.com/test/question/done?tid=4191901&qid=22467#summary>

HashTable和HashMap区别

第一,继承不同。

public class Hashtable extends Dictionary implements Map

public class HashMap  extends AbstractMap implements Map

第二

Hashtable 中的方法是同步的,而HashMap中的方法在缺省情况下是非同步的。在多线程并发的环境下,可以直接使用Hashtable,但是要使用HashMap的话就要自己增加同步处理了。

第三

Hashtable中,key和value都不允许出现null值。

在HashMap中,null可以作为键,这样的键只有一个;可以有一个或多个键所对应的值为null。当get()方法返回null值时,即可以表示 HashMap中没有该键,也可以表示该键所对应的值为null。因此,在HashMap中不能由get()方法来判断HashMap中是否存在某个键, 而应该用containsKey()方法来判断。

第四,两个遍历方式的内部实现上不同。

Hashtable、HashMap都使用了 Iterator。而由于历史原因,Hashtable还使用了Enumeration的方式 。

第五

哈希值的使用不同,HashTable直接使用对象的hashCode。而HashMap重新计算hash值。

第六

Hashtable和HashMap它们两个内部实现方式的数组的初始大小和扩容的方式。HashTable中hash数组默认大小是11,增加的方式是 old*2+1。HashMap中hash数组的默认大小是16,而且一定是2的指数。

 

来自 <http://www.cnblogs.com/devinzhang/archive/2012/01/13/2321481.html>

 

List接口中的对象按一定顺序排列,允许重复

Set接口中的对象没有顺序,但是不允许重复

Map接口中的对象是key、value的映射关系,key不允许重复

Map接口和Collection接口是同一等级的

来自 <http://www.nowcoder.com/test/question/done?tid=4197314&qid=15001#summary>

 

Properties继承自HashTable,是线程安全的。Properties中的 Store()方法把一个Properties对象的内容以一种可读的形式保存到一个文件中。Load()方法正好相反,用来读取文件,并设定Properties对象来包含keys和values。

Properties类用来方便 的读写配置文件,支持key-value形式和xml形式的配置文件,以key-value为例, Properties的load方法直接将文件读取到内存中并且以map形式来保存,用 getProperty(“key”)方法来取得对应的vaule值。

 

来自 <http://www.nowcoder.com/test/question/done?tid=4197314&qid=16019#summary>

 

关于String,StringBuilder以及StringBuffer:

对String对象的任何改变都不影响到原对象,相关的任何change操作都会生成新的对象

StringBuffer是线程安全的StringBuilder

StringBuilder跟StringBuffer功能相同,区别是StringBuilder不是线程安全的

StringBuilder和StringBuffer底层都是以字符数组存放的,可以修改内容

线程安全:(Buffer是一个资源,有锁访问的,线程安全的)

非线程安全的情况:当A获取到这条数据,准备修改时,B线程进来了,校验完数据,发现数据不正确,就把数据移除了,这时A线程仍旧认为当前持有的数据还是开始获取的数据,这样再做处理就会报空了。

线程安全的情况:就是当一个线程需要对这个数据进行改写时,会给这个数据上一个同步锁,比如A线程拿到数据后,给数据加上同步锁,这时候B线程进来了,但是这时候数据已经上锁,B线程则需要等待A线程释放锁之后才能对数据进行操作,这样就防止了脏数据的产生。

来自 <http://www.nowcoder.com/test/question/done?tid=4192217&qid=15539#summary>

 

线程通过调用对象中synchronized的方法可获得对象的互斥锁定

线程调度算法是平台独立的:线程调度分为协同式调度和抢占式调度,Java使用的是抢占式调度,也就是每个线程将由操作系统来分配执行时间,线程的切换不由线程本身来决定(协同式调度)。这就是平台独立的原因。

来自 <http://www.nowcoder.com/test/question/done?tid=4192217&qid=26053#summary>

 

sleep和wait的区别有:

(调用sleep()方法的过程中,线程不会释放对象锁,调用wait()方法的时候,线程会放弃对象锁,sleep()方法导致了线程暂停执行指定的时间,但不会让出cpu给其他线程)

1、这两个方法来自不同的类分别是,sleep来自Thread类,和wait来自Object类。

sleep是Thread的静态类方法,谁调用的谁去睡觉,即使在a线程里调用了b的sleep方法,实际上还是a去睡觉,要让b线程睡觉要在b的代码中调用sleep。

2、 最主要是sleep方法没有释放锁,而wait方法释放了锁,使得敏感词线程可以使用同步控制块或者方法。

sleep不出让系统资源;wait是进入线程等待池等待,出让系统资源敏感词线程可以占用CPU。一般wait不会加时间限制,因为如果wait线程的运行资源不够,再出来也没用,要等待敏感词线程调用notify/notifyAll唤醒等待池中的所有线程,才会进入就绪队列等待OS分配系统资源。sleep(milliseconds)可以用时间指定使它自动唤醒过来,如果时间不到只能调用interrupt()强行打断。

Thread.Sleep(0)的作用是“触发操作系统立刻重新进行一次CPU竞争”。

3、使用范围:wait,notify和notifyAll只能在同步控制方法或者同步控制块里面使用,而sleep可以在任何地方使用

synchronized(x){

x.notify()

//或者wait()

}

4、sleep必须捕获异常,而wait,notify和notifyAll不需要捕获异常

来自 <http://www.nowcoder.com/test/question/done?tid=4193149&qid=14364#summary>

 

快速失败(Fail-Fast)机制:对于线程不安全的集合对象的迭代器,如果在使用迭代器的过程中有其他线程修改了集合对象结构或者元素数量,那么将抛出ConcurrentModificationException,这就是所谓fail-fast策略。

迭代 HashMap 采用快速失败机制,而 HashTable 不是,因为 HashTable 是线程安全的。

来自 <http://www.nowcoder.com/test/question/done?tid=4193149&qid=15548#summary>

 

JSP九大内置对象有:

1.request对象

客户端的请求信息被封装在request对象中,通过它才能了解到客户的需求,然后做出响应。它是HttpServletRequest类的实例。

2.response对象

response对象包含了响应客户请求的有关信息,但在JSP中很少直接用到它。它是HttpServletResponse类的实例。

3.session对象

session对象指的是客户端与服务器的一次会话,从客户连到服务器的一个WebApplication开始,直到客户端与服务器断开连接为止。它是HttpSession类的实例.

4.out对象

out对象是JspWriter类的实例,是向客户端输出内容常用的对象

5.page对象

page对象就是指向当前JSP页面本身,有点象类中的this指针,它是java.lang.Object类的实例

6.application对象

application对象实现了用户间数据的共享,可存放全局变量。它开始于服务器的启动,直到服务器的关闭,在此期间,此对象将一直存在;这样在用户的前后连接或不同用户之间的连接中,可以对此对象的同一属性进行操作;在任何地方对此对象属性的操作,都将影响到其他用户对此的访问。服务器的启动和关闭决定了application对象的生命。它是ServletContext类的实例。

7.exception对象

exception对象是一个例外对象,当一个页面在运行过程中发生了例外,就产生这个对象。如果一个JSP页面要应用此对象,就必须把isErrorPage设为true,否则无法编译。他实际上是java.lang.Throwable的对象

8.pageContext对象

pageContext对象提供了对JSP页面内所有的对象及名字空间的访问,也就是说他可以访问到本页所在的SESSION,也可以取本页面所在的application的某一属性值,他相当于页面中所有功能的集大成者,它的本 类名也叫pageContext。

9.config对象

config对象是在一个Servlet初始化时,JSP引擎向它传递信息用的,此信息包括Servlet初始化时所要用到的参数(通过属性名和属性值构成)以及服务器的有关信息(通过传递一个ServletContext对象)

 

pageContext javax.servlet.jsp.PageContext

request javax.servlet.http.HttpServletRequest

response javax.servlet.http.HttpServletResponse

session javax.servlet.http.HttpSession

application javax.servlet.ServletContext

config javax.serlvet.ServletConfig

exception java.lang.Throwable

page java.lang.Object

out javax.servlet.jsp.JspWriter

作用:

1、pageContext 表示页容器 EL表达式、 标签 、上传

2、request 服务器端取得客户端的信息:头信息 、Cookie 、请求参数 ,最大用处在MVC设计模式上

3、response 服务器端回应客户端信息:Cookie、重定向

4、session 表示每一个用户,用于登录验证上

5、application 表示整个服务器

6、config 取得初始化参数,初始化参数在web.xml文件中配置

7、exception 表示的是错误页的处理操作

8、page 如同this一样,代表整个jsp页面自身

9、out 输出 ,但是尽量使用表达式输出

来自 <http://www.nowcoder.com/test/question/done?tid=4193149&qid=15240#summary>

 

PreparedStatement与Statement区别:

创建时的区别:

Statement statement = conn.createStatement();

PreparedStatement preStatement = conn.prepareStatement(sql);

执行时的区别:

ResultSet rSet = statement.executeQuery(sql);

ResultSet pSet = preStatement.executeQuery();

由上可以看出,PreparedStatement有预编译的过程,已经绑定sql,之后无论执行多少遍,都不会再去进行编译,

而 statement 不同,如果执行多变,则相应的就要编译多少遍sql,所以从这点看,preStatement 的效率会比 Statement要高一些

来自 <http://www.nowcoder.com/test/question/done?tid=4194265&qid=25808#summary>

 

Collection和Collections区别:

java.util.Collection 是一个集合接口。它提供了对集合对象进行基本操作的通用接口方法。Collection接口在Java 类库中有很多具体的实现。Collection接口的意义是为各种具体的集合提供了最大化的统一操作方式。

java.util.Collections 是一个包装类。它包含有各种有关集合操作的静态多态方法。此类不能实例化,就像一个工具类,服务于Java的Collection框架。

 

来自 <http://www.nowcoder.com/test/question/done?tid=4194265&qid=7694#summary>

 

JAVA的基本类型

 默认值 存储需求(字节) 取值范围  示例
byte 0 1  -2^7—2^7-1 byte b=10;
char  ‘ \u0000′ 2  0—2^16-1 char c=’c’ ;
short 0 2 -2^15—2^15-1 short s=10;
int 0 4 -2^31—2^31-1 int i=10;
long 0 8 -2^63—2^63-1 long o=10L;
float  0.0f 4 -2^31—2^31-1 float f=10.0F
double 0.0d 8 -2^63—2^63-1 double d=10.0;
boolean false 1 true\false boolean flag=true;

来自 <http://www.nowcoder.com/test/question/done?tid=4197314&qid=14974#summary>

 

 

J2EE中常用的名词解释

1.web容器:给处于其中的应用程序组件(JSP,SERVLET)提供一个环境,使JSP,SERVLET直接和容器中的环境变量接接口互,不必关注其它系统问题。主要有WEB服务器来实现。例如:TOMCAT,WEBLOGIC,WEBSPHERE等。该容器提供的接口严格遵守J2EE规范中的WEB APPLICATION 标准。我们把遵守以上标准的WEB服务器就叫做J2EE中的WEB容器。

2.Web container:实现J2EE体系结构中Web组件协议的容器。这个协议规定了一个Web组件运行时的环境,包括安全,一致性,生命周期管理,事务,配置和其它的服务。一个提供和JSP和J2EE平台APIs界面相同服务的容器。一个Web container 由Web服务器或者J2EE服务器提供。

3.EJB容器:Enterprise java bean 容器。更具有行业领域特色。他提供给运行在其中的组件EJB各种管理功能。只要满足J2EE规范的EJB放入该容器,马上就会被容器进行高效率的管理。并且可以通过现成的接口来获得系统级别的服务。例如邮件服务、事务管理。一个实现了J2EE体系结构中EJB组件规范的容器。 这个规范指定了一个Enterprise bean的运行时环境,包括安全,一致性,生命周期,事务, 配置,和其他的服务。

4.JNDI:(Java Naming & Directory Interface)JAVA命名目录服务。主要提供的功能是:提供一个目录系统,让其它各地的应用程序在其上面留下自己的索引,从而满足快速查找和定位分布式应用程序的功能。

5.JMS:(Java Message Service)JAVA消息服务。主要实现各个应用程序之间的通讯。包括点对点和广播。

6.JTA:(Java Transaction API)JAVA事务服务。提供各种分布式事务服务。应用程序只需调用其提供的接口即可。

7.JAF:(Java Action FrameWork)JAVA安全认证框架。提供一些安全控制方面的框架。让开发者通过各种部署和自定义实现自己的个性安全控制策略。

8.RMI/IIOP:(Remote Method Invocation /internet对象请求中介协议)他们主要用于通过远程调用服务。例如,远程有一台计算机上运行一个程序,它提供股票分析服务,我们可以在本地计算机上实现对其直接调用。当然这是要通过一定的规范才能在异构的系统之间进行通信。RMI是JAVA特有的。RMI-IIOP出现以前,只有RMI和CORBA两种选择来进行分布式程序设计。RMI-IIOP综合了RMI和CORBA的优点,克服了他们的缺点,使得程序员能更方便的编写分布式程序设计,实现分布式计算。首先,RMI-IIOP综合了RMI的简单性和CORBA的多语言性(兼容性),其次RMI-IIOP克服了RMI只能用于Java的缺点和CORBA的复杂性(可以不用掌握IDL)。

 

来自 <http://www.nowcoder.com/test/question/done?tid=4197314&qid=15393#summary>

 

servlet生命周期:init 、service、destory

init整个程序启动时候执行一次

destroy退出程序进行销毁时候执行

service用户端运行JSP时方法都会运行一次

JSP会先解释成Servlet源文件,然后编译成Servlet类文件

来自 <http://www.nowcoder.com/test/question/done?tid=4199094&qid=15253#summary>

 

静态include和动态include区别:

动态include用 jsp:include 动作实现 <jsp:include page=”included.jsp” flush=”true” /> 它总是会检查所含文件中的变化 , 适合用于包含动态页面,并且可以带参数。各个文件分别先编译,然后组合成一个文件。

静态include用 include 伪码实现 , 定不会检查所含文件的变化 , 适用于包含静态页面 <%@ include file=”included.htm” %>。先将文件的代码被原封不动地加入到了主页面从而合成一个文件,然后再进行翻译,此时不允许有相同的变量。

以下是对include两种用法的区别,主要有两个方面的不同 ;

一 : 执行时间上 :

<%@ include file=”relativeURI”%> 是在翻译阶段执行

<jsp:include page=”relativeURI” flush=”true” /> 在请求处理阶段执行 .

二 : 引入内容的不同 :

<%@ include file=”relativeURI”%>

引入静态文本 (html,jsp), 在 JSP 页面被转化成 servlet 之前和它融和到一起 .

<jsp:include page=”relativeURI” flush=”true” /> 引入执行页面或 servlet 所生成的应答文本。

来自 <http://www.nowcoder.com/test/question/done?tid=4199094&qid=15383#summary>

 

instanceof是java的二元运算符,用来判断他左边的对象是否为右面类(接口,抽象类,父类)的实例

来自 <http://www.nowcoder.com/test/question/done?tid=4199094&qid=26050#summary>

 

java Thread中start方法和run方法区别:

1.start方法

用 start方法来启动线程,是真正实现了多线程, 通过调用Thread类的start()方法来启动一个线程,这时此线程处于就绪(可运行)状态,并没有运行,一旦得到cpu时间片,就开始执行run()方法。但要注意的是,此时无需等待run()方法执行完毕,即可继续执行下面的代码。所以run()方法并没有实现多线程。

2.run方法

run()方法只是类的一个普通方法而已,如果直接调用Run方法,程序中依然只有主线程这一个线程,其程序执行路径还是只有一条,还是要顺序执行,还是要等待run方法体执行完毕后才可继续执行下面的代码。

来自 <http://www.nowcoder.com/test/question/done?tid=4199094&qid=14311#summary>

 

首先final声明的方法是不能被覆盖的,但是这里并不错误,因为方法是private的,也就是子类没有继承父类的run方法,因此子类的run方法跟父类的run方法无关,并不是覆盖。new Car().run()也是调用子类的run方法。(参考链接题目)

来自 <http://www.nowcoder.com/test/question/done?tid=4199094&qid=3229#summary>

 

Session对象在ASP中默认有效为20分钟

JSP使用TomCat服务器,默认为30分钟

来自 <http://www.nowcoder.com/test/question/done?tid=4200567&qid=13704#summary>

 

编码转换:

实现GBK编码字节流到UTF-8编码字节流的转换:(byte[] src,dst;)

dst=new String(src,”GBK”).getBytes(“UTF-8”)

另一种:new String(String.getBytes(“ISO8859-1″),GB2312)

来自 <http://www.nowcoder.com/test/question/done?tid=4201903&qid=15390#summary>

来自 <http://www.nowcoder.com/test/question/done?tid=4200567&qid=16018#summary>

 

sleep是线程类(Thread)的方法,执行此方法会导致当前此线程暂停指定时间,给执行机会给其他线程,但是监控状态依然保持,到时后会自动恢复。调用sleep不会释放对象锁。

wait是Object类的方法,对此对象调用wait方法导致本线程放弃对象锁,进入等待此对象的等待锁定池,只有针对此对象发出notify方法或notifyAll后本线程才进入对象锁定池(就绪状态)准备获得对象锁进入运行状态

来自 <http://www.nowcoder.com/test/question/done?tid=4201263&qid=15267#summary>

 

Servlet 与 CGI 的比较

和CGI程序一样,Servlet可以响应用户的指令(提交一个FORM等等),也可以象CGI程序一样,收集用户表单的信息并给予动态反馈(简单的注册信息录入和检查错误)。

然而,Servlet的机制并不仅仅是这样简单的与用户表单进行交互。传统技术中,动态的网页建立和显示都是通过CGI来实现的,但是,有了Servlet,您可以大胆的放弃所有CGI(perl?php?甚至asp!),利用Servlet代替CGI,进行程序编写。

对比一:当用户浏览器发出一个Http/CGI的请求,或者说 调用一个CGI程序的时候,服务器端就要新启用一个进程 (而且是每次都要调用),调用CGI程序越多(特别是访问量高的时候),就要消耗系统越多的处理时间,只剩下越来越少的系统资源,对于用户来说,只能是漫长的等待服务器端的返回页面了,这对于电子商务激烈发展的今天来说,不能不说是一种技术上的遗憾。

Servlet充分发挥了服务器端的资源并高效的利用。每次调用Servlet时并不是新启用一个进程 ,而是在一个Web服务器的进程敏感词享和分离线程,而线程最大的好处在于可以共享一个数据源,使系统资源被有效利用。

对比二:传统的CGI程序,不具备平台无关性特征,系统环境发生变化,CGI程序就要瘫痪,而Servlet具备Java的平台无关性,在系统开发过程中保持了系统的可扩展性、高效性。

对比三:传统技术中,一般大都为二层的系统架构,即Web服务器+数据库服务器,导致网站访问量大的时候,无法克服CGI程序与数据库建立连接时速度慢的瓶颈,从而死机、数据库死锁现象频繁发生。而我们的Servlet有连接池的概念,它可以利用多线程的优点,在系统缓存中事先建立好若干与数据库的连接,到时候若想和数据库打交道可以随时跟系统”要”一个连接即可,反应速度可想而知。

 

CGI不可移植,为某一特定平台编写的CGI应用只能运行于这一环境中。每一个CGI应用存在于一个由客户端请求激活的进程中,并且在请求被服务后被卸载。这种模式将引起很高的内存、CPU开销,而且在同一进程中不能服务多个客户。

来自 <http://www.nowcoder.com/test/question/done?tid=4201263&qid=15033#summary>

 

Cookie和Session

Cookie是Web服务器发送给客户端的一小段信息,客户端请求时,可以读取该信息发送到服务器端。

关闭浏览器意味着会话ID丢失,但所有与原会话关联的会话数据仍保留在服务器上,直至会话过期。

在禁用Cookie时可以使用URL重写技术跟踪会话。

每个Session对象都有一个唯一Id,存储在客户端的cookie中(cookie时间默认为-1,即cookie保存在浏览器缓存里)

如果客户端禁用cookie,可以使用url重写的方式使用Session

来自 <http://www.nowcoder.com/test/question/done?tid=4201903&qid=15264#summary>

 

以下JSP代码定义了一个变量,如何输出这个变量的值?

<bean:define id=”stringBean” value=”helloWorld”/>

答案:

      1. <%=stringBean%>
      2. <bean:write name=”stringBean”/>
      3. <%String myBean=(String)pageContext.getAttribute(“stringBean”,PageContext.PAGE_SCOPE);%>
        <%=myBean%>

来自 <http://www.nowcoder.com/test/question/done?tid=4201903&qid=25706#summary>

 

Servlet的生命周期分为5个阶段:加载、创建、初始化、处理客户请求、卸载。

(1)加载:容器通过类加载器使用servlet类对应的文件加载servlet

(2)创建:通过调用servlet构造函数创建一个servlet对象

(3)初始化:调用init方法初始化

(4)处理客户请求:每当有一个客户请求,容器会创建一个线程来处理客户请求

(5)卸载:调用destroy方法让servlet自己释放其占用的资源

其中创建Servlet的实例是由Servlet容器来完成的,且创建Servlet实例是在初始化方法init()之前

来自 <http://www.nowcoder.com/test/question/done?tid=4201903&qid=15042#summary>

 

checked exception:指的是编译时异常,该类异常需要本函数必须处理的,用try和catch处理,或者用throws抛出异常,然后交给调用者去处理异常。

runtime exception:指的是运行时异常,该类异常不必须本函数必须处理,当然也可以处理。

Thread.sleep()抛出的InterruptException属于checked exception;IllegalArgumentException属于Runtime exception;

Thread.sleep()和 Object.wait(),都可以抛出 InterruptedException。这个异常是不能忽略的,因为它是一个检查异常(checked exception)

来自 <http://www.nowcoder.com/test/question/done?tid=4223306&qid=3233#summary>

 

java的垃圾收集机制主要针对新生代和老年代的内存进行回收,不同的垃圾收集算法针对不同的区域。所以java的垃圾收集算法使用的是分代回收。一般java的对象首先进入新生代的Eden区域,当进行GC的时候会回收新生代的区域,新生代一般采用复制收集算法,将活着的对象复制到survivor区域中,如果survivor区域装在不下,就查看老年代是否有足够的空间装下新生代中的对象,如果能装下就装下,否则老年代就执行FULL GC回收自己,老年代还是装不下,就会抛出OUtOfMemory的异常

来自 <http://www.nowcoder.com/test/question/done?tid=4223940&qid=2970>

 

定义在类中的变量是类的成员变量,可以不进行初始化,Java会自动进行初始化,如果是引用类型默认初始化为null,如果是基本类型例如int则会默认初始化为0

局部变量是定义在方法中的变量,必须要进行初始化,否则不同通过编译

被static关键字修饰的变量是静态的,静态变量随着类的加载而加载,所以也被称为类变量

被final修饰发变量是常量

来自 <http://www.nowcoder.com/test/question/done?tid=4223940&qid=14981#summary>

 

我们知道文件都有文件名与数据,这在 Linux 上被分成两个部分:用户数据 (user data) 与元数据 (metadata)。用户数据,即文件数据块 (data block),数据块是记录文件真实内容的地方;而元数据则是文件的附加属性,如文件大小、创建时间、所有者等信息。在 Linux 中,元数据中的 inode 号(inode 是文件元数据的一部分但其并不包含文件名,inode 号即索引节点号)才是文件的唯一标识而非文件名。文件名仅是为了方便人们的记忆和使用,系统或程序通过 inode 号寻找正确的文件数据块。

硬链接 (hard link) 与软链接(又称符号链接,即 soft link 或 symbolic link)。链接为 Linux 系统解决了文件的共享使用,还带来了隐藏文件路径、增加权限安全及节省存储等好处。

若一个 inode 号对应多个文件名,则称这些文件为硬链接。换言之,硬链接就是同一个文件使用了多个别名。

若文件用户数据块中存放的内容是另一文件的路径名的指向,则该文件就是软链接。

来自 <http://www.nowcoder.com/test/question/done?tid=4223940&qid=14819#summary>

 

两个最基本的java回收算法:复制算法和标记清理算法

复制算法:两个区域A和B,初始对象在A,继续存活的对象被转移到B。此为新生代最常用的算法

标记清理:一块区域,标记要回收的对象,然后回收,一定会出现碎片,那么引出

标记-整理算法:多了碎片整理,整理出更大的内存放更大的对象

两个概念:新生代和年老代

新生代:初始对象,生命周期短的

永久代:长时间存在的对象

整个java的垃圾回收是新生代和年老代的协作,这种叫做分代回收。

Serial New收集器是针对新生代的收集器,采用的是复制算法

Parallel New(并行)收集器,新生代采用复制算法,老年代采用标记整理

Parallel  Scavenge(并行)收集器,针对新生代,采用复制收集算法

Serial Old(串行)收集器,新生代采用复制,老年代采用标记清理

Parallel   Old(并行)收集器,针对老年代,标记整理

CMS收集器,基于标记清理

G1收集器:整体上是基于标记清理,局部采用复制

详细:

1.Serial New/Serial Old

Serial/Serial Old收集器是最基本最古老的收集器,它是一个单线程收集器,并且在它进行垃圾收集时,必须暂停所有用户线程。Serial New收集器是针对新生代的收集器,采用的是Copying算法,Serial Old收集器是针对老年代的收集器,采用的是Mark-Compact算法。它的优点是实现简单高效,但是缺点是会给用户带来停顿。

2.Parallel New

Parallel New收集器是Serial收集器的多线程版本(参照Serial New),使用多个线程进行垃圾收集。

3.Parallel Scavenge

Parallel Scavenge收集器是一个新生代的多线程收集器(并行收集器),它在回收期间不需要暂停其他用户线程,其采用的是Copying算法,该收集器与前两个收集器有所不同,它主要是为了达到一个可控的吞吐量。

4.Parallel Old

Parallel Old是Parallel Scavenge收集器的老年代版本(并行收集器),使用多线程和Mark-Compact算法。

5.CMS

CMS(Current Mark Sweep)收集器是一种以获取最短回收停顿时间为目标的收集器,它是一种并发收集器,采用的是Mark-Sweep算法。

6.G1

G1收集器是当今收集器技术发展最前沿的成果,它是一款面向服务端应用的收集器,它能充分利用多CPU、多核环境。因此它是一款并行与并发收集器,并且它能建立可预测的停顿时间模型。

 

来自 <http://www.nowcoder.com/test/question/done?tid=4223940&qid=36411#summary>

 

同步方法和同步代码块的区别是什么?

同步方法 ( 粗粒度锁 ):

  1. 修饰一般方法 : public synchronized void method (){…}, 获取的是当前调用对象 this 上的锁
  2. 修饰静态方法 : public static synchronized void method (){…}, 获取当前类的字节码对象上的锁

同步代码块 ( 细粒度锁 ):

synchronized ( obj ) {…}, 同步代码块可以指定获取哪个对象上的锁 , obj 任意

来自 <http://www.nowcoder.com/test/question/done?tid=4237560&qid=15330#summary>

 

java.lang包是java语言包,由解释器自动引入。

java.util包,java的工具包,需要手动导入。

java.sql包,JDBC接口类,需要手动导入。

java.io包,各种输入输入流,需要手动导入。

来自 <http://www.nowcoder.com/test/question/done?tid=4239064&qid=15124#summary>

 

只要记住protected一个特点是只要子类都能访问,不管在不在一个包。

来自 <http://www.nowcoder.com/test/question/done?tid=4239064&qid=25799#summary>

 

1.为什么使用内部类?

使用内部类最吸引人的原因是:每个内部类都能独立地继承一个(接口的)实现,所以无论外围类是否已经继承了某个(接口的)实现,

对于内部类都没有影响

1.1.使用内部类最大的优点就在于它能够非常好的解决多重继承的问题,使用内部类还能够为我们带来如下特性:

(1)、内部类可以用多个实例,每个实例都有自己的状态信息,并且与其他外围对象的信息相互独。

(2)、在单个外围类中,可以让多个内部类以不同的方式实现同一个接口,或者继承同一个类。

(3)、创建内部类对象的时刻并不依赖于外围类对象的创建。

(4)、内部类并没有令人迷惑的“is-a”关系,他就是一个独立的实体。

(5)、内部类提供了更好的封装,除了该外围类,其他类都不能访问。

2.内部类分类:

(一).成员内部类:

 

1

2

3

4

5

6

7

8

9

10

11

12

13

14

15

16

17

18

19

20

public class Outer{

private int age = 99;

String name = “Coco”;

public class Inner{

String name = “Jayden”;

public void show(){

System.out.println(Outer.this.name);

System.out.println(name);

System.out.println(age);

}

}

public Inner getInnerClass(){

return new Inner();

}

public static void main(String[] args){

Outer o = new Outer();

Inner in = o.new Inner();

in.show();

}

}

1.Inner 类定义在 Outer 类的内部,相当于 Outer 类的一个成员变量的位置,Inner 类可以使用任意访问控制符,

如 public 、 protected 、 private 等

2.Inner 类中定义的 show() 方法可以直接访问 Outer 类中的数据,而不受访问控制符的影响,

如直接访问 Outer 类中的私有属性age

3.定义了成员内部类后,必须使用外部类对象来创建内部类对象,而不能直接去 new 一个内部类对象,

即:内部类 对象名 = 外部类对象.new 内部类( );

4.编译上面的程序后,会发现产生了两个 .class 文件: Outer.class,Outer$Inner.class{}

5.成员内部类中不能存在任何 static 的变量和方法,可以定义常量:

(1).因为非静态内部类是要依赖于外部类的实例,而静态变量和方法是不依赖于对象的,仅与类相关,

简而言之:在加载静态域时,根本没有外部类,所在在非静态内部类中不能定义静态域或方法,编译不通过;

非静态内部类的作用域是实例级别

(2).常量是在编译器就确定的,放到所谓的常量池了

★★友情提示:

1.外部类是不能直接使用内部类的成员和方法的,可先创建内部类的对象,然后通过内部类的对象来访问其成员变量和方法;

2.如果外部类和内部类具有相同的成员变量或方法,内部类默认访问自己的成员变量或方法,如果要访问外部类的成员变量,

可以使用 this 关键字,如:Outer.this.name

(二).静态内部类: 是 static 修饰的内部类,

1.静态内部类不能直接访问外部类的非静态成员,但可以通过 new 外部类().成员 的方式访问

2.如果外部类的静态成员与内部类的成员名称相同,可通过“类名.静态成员”访问外部类的静态成员;

如果外部类的静态成员与内部类的成员名称不相同,则可通过“成员名”直接调用外部类的静态成员

3.创建静态内部类的对象时,不需要外部类的对象,可以直接创建 内部类 对象名 = new 内部类();

 

1

2

3

4

5

6

7

8

9

10

11

12

13

14

15

public class Outer{

private int age = 99;

static String name = “Coco”;

public static class Inner{

String name = “Jayden”;

public void show(){

System.out.println(Outer.name);

System.out.println(name);

}

}

public static void main(String[] args){

Inner i = new Inner();

i.show();

}

}

(三).方法内部类:访问仅限于方法内或者该作用域内

(1).局部内部类就像是方法里面的一个局部变量一样,是不能有 public、protected、private 以及 static 修饰符的

(2).只能访问方法中定义的 final 类型的局部变量,因为:

当方法被调用运行完毕之后,局部变量就已消亡了。但内部类对象可能还存在,

直到没有被引用时才会消亡。此时就会出现一种情况,就是内部类要访问一个不存在的局部变量;

==>使用final修饰符不仅会保持对象的引用不会改变,而且编译器还会持续维护这个对象在回调方法中的生命周期.

局部内部类并不是直接调用方法传进来的参数,而是内部类将传进来的参数通过自己的构造器备份到了自己的内部,

自己内部的方法调用的实际是自己的属性而不是外部类方法的参数;

防止被篡改数据,而导致内部类得到的值不一致

 

1

2

3

4

5

6

7

8

9

10

11

12

13

14

15

16

17

18

19

20

21

22

23

24

25

26

   /*

使用的形参为何要为 final???

在内部类中的属性和外部方法的参数两者从外表上看是同一个东西,但实际上却不是,所以他们两者是可以任意变化的,

也就是说在内部类中我对属性的改变并不会影响到外部的形参,而然这从程序员的角度来看这是不可行的,

毕竟站在程序的角度来看这两个根本就是同一个,如果内部类该变了,而外部方法的形参却没有改变这是难以理解

和不可接受的,所以为了保持参数的一致性,就规定使用 final 来避免形参的不改变

*/

public class Outer{

public void Show(){

final int a = 25;

int b = 13;

class Inner{

int c = 2;

public void print(){

System.out.println(“访问外部类:” + a);

System.out.println(“访问内部类:” + c);

}

}

Inner i = new Inner();

i.print();

}

public static void main(String[] args){

Outer o = new Outer();

o.show();

}

}

(四).匿名内部类:

(1).匿名内部类是直接使用 new 来生成一个对象的引用;

(2).对于匿名内部类的使用它是存在一个缺陷的,就是它仅能被使用一次,创建匿名内部类时它会立即创建一个该类的实例,该类的定义会立即消失,所以匿名内部类是不能够被重复使用;

(3).使用匿名内部类时,我们必须是继承一个类或者实现一个接口,但是两者不可兼得,同时也只能继承一个类或者实现一个接口;

(4).匿名内部类中是不能定义构造函数的,匿名内部类中不能存在任何的静态成员变量和静态方法;

(5).匿名内部类中不能存在任何的静态成员变量和静态方法,匿名内部类不能是抽象的,它必须要实现继承的类或者实现的接口的所有抽象方法

(6).匿名内部类初始化:使用构造代码块!利用构造代码块能够达到为匿名内部类创建一个构造器的效果

 

1

2

3

4

5

6

7

8

9

10

11

12

13

14

15

16

17

18

  public class OuterClass {

public InnerClass getInnerClass(final int   num,String str2){

return new InnerClass(){

int number = num + 3;

public int getNumber(){

return number;

}

};        /* 注意:分号不能省 */

}

public static void main(String[] args) {

OuterClass out = new OuterClass();

InnerClass inner = out.getInnerClass(2, “chenssy”);

System.out.println(inner.getNumber());

}

}

interface InnerClass {

int getNumber();

}

来自 <http://www.nowcoder.com/questionTerminal/48524c47dd924887be6684b17175fa40>

 

方法的重写(override两同两小一大原则

方法名相同,参数类型相同

子类返回类型小于等于父类方法返回类型,

子类抛出异常小于等于父类方法抛出异常,

子类访问权限大于等于父类方法访问权限。

来自 <http://www.nowcoder.com/test/question/done?tid=4239064&qid=4330#summary>

 

实现线程间通知和唤醒:

Object.wait/notify/notifyAll

Condition.await/signal/signalAll

wait()notify()notifyAll() Object 中的方法

Condition是在java 1.5中才出现的,它用来替代传统的Objectwait()notify()实现线程间的协作,相比使用Objectwait()notify(),使用Condition1await()signal()这种方式实现线程间协作更加安全和高效。

来自 <http://www.nowcoder.com/test/question/done?tid=4244085&qid=3255#summary>

 

 

synchronized 关键字 : 用来给对象和方法或者代码块加锁,当它锁定一个方法或者一个代码块的时候,同一时刻最多只有一个线程执行这个段代码。

volatile:用来确保将变量的跟新操作通知到其他线程,当把变量声明为volatile类型后,编译器与运行时都会注意到这个变量是共享的,因此不会将该变量上的操作与其他内存操作一起重排序。然而,在访问volatile变量时不会执行加锁操作,因此也就不会使执行线程阻塞,因此volatile变量是一种比 synchronized关键字更轻量级的同步机制。

serialize:Java 对象序列化为二进制文件。

static关键字: static关键字可以修饰变量,方法,静态代码块。

静态变量:               由static修饰的变量称为静态变量

静态变量属于类,而不属于某个对象

静态变量它的副本只有一个(静态变量在类中只加载一)

 

静态方法:               在静态方法中只能调用静态变量和静态方法

在非静态方法中,可以调用静态方法或者变量。

在静态方法中不能使用this和super关键字。

 

静态代码块                  作用:用来给静态成员变量初始化

 

来自 <http://www.nowcoder.com/test/question/done?tid=4244085&qid=15544#summary>

 

环境变量可在编译source code时指定

javac一次可同时编译数个Java源文件

javac.exe能指定编译结果要置于哪个目录(directory)

来自 <http://www.nowcoder.com/test/question/done?tid=4256437&qid=973#summary>

 

ArrayList的构造函数总共有三个:

(1)ArrayList()构造一个初始容量为 10 的空列表。

(2)ArrayList(Collection<? extends E> c)构造一个包含指定 collection 的元素的列表,这些元素是按照该 collection 的迭代器返回它们的顺序排列的。

(3)ArrayList(int initialCapacity)构造一个具有指定初始容量的空列表。

来自 <http://www.nowcoder.com/test/question/done?tid=4256437&qid=22465#summary>

 

关于ArrayList()的扩容:(不确定)

ArrayList的默认初始容量为10,当然也可以自定义指定初始容量,随着动态的向其中添加元素,其容量可能会动态的增加,那么扩容的公式为:

新容量 = 旧容量/2 + 旧容量 + 1

比如:初始容量为4,其容量的每次扩充后的新容量为:4->7->11->17->26->…

附:HashMap的初始容量大小为16

来自 <http://www.nowcoder.com/questionTerminal/85bf28c36fa14484b950f07d269dcd49>

 

struct1和struct2区别:

从action类上分析:

1.Struts1要求Action类继承一个抽象基类。Struts1的一个普遍问题是使用抽象类编程而不是接口。

  1. Struts 2 Action类可以实现一个Action接口,也可实现其他接口,使可选和定制的服务成为可能。Struts2提供一个ActionSupport基类去实现常用的接口。Action接口不是必须的,任何有execute标识的POJO对象都可以用作Struts2的Action对象。

从Servlet 依赖分析:

  1. Struts1 Action 依赖于Servlet API ,因为当一个Action被调用时HttpServletRequest 和 HttpServletResponse 被传递给execute方法。
  2. 4. Struts 2 Action不依赖于容器,允许Action脱离容器单独被测试。如果需要,Struts2 Action仍然可以访问初始的request和response。但是,其他的元素减少或者消除了直接访问HttpServetRequest 和 HttpServletResponse的必要性。

从action线程模式分析:

  1. Struts1 Action是单例模式并且必须是线程安全的,因为仅有Action的一个实例来处理所有的请求。单例策略限制了Struts1 Action能作的事,并且要在开发时特别小心。Action资源必须是线程安全的或同步的。
  2. Struts2 Action对象为每一个请求产生一个实例,因此没有线程安全问题。(实际上,servlet容器给每个请求产生许多可丢弃的对象,并且不会导致性能和垃圾回收问题)

来自 <http://www.nowcoder.com/test/question/done?tid=4256437&qid=15081#summary>

 

ConcurrentHashMap使用segment来分段和管理锁,segment继承自ReentrantLock,因此ConcurrentHashMap使用ReentrantLock来保证线程安全。

Arrays.asList()将一个数组转化为一个List对象,这个方法会返回一个ArrayList类型的对象, 这个ArrayList类并非!!!java.util.ArrayList类,而是Arrays类的静态内部类!用这个对象对列表进行添加删除更新操作,就会报UnsupportedOperationException异常。

SimpleDateFormat对象是线程不安全的

来自 <http://www.nowcoder.com/test/question/done?tid=4269423&qid=26113#summary>

 

下面几种数组复制方法中,哪个效率最高? 答案:System.arraycopy()

1、System.arraycopy()源码可以看到是native方法:native关键字说明其修饰的方法是一个原生态方法,方法对应的实现不是在当前文件,而是在用其他语言(如C和C++)实现的文件中。 可以将native方法比作Java程序同C程序的接口。

public static native void arraycopy(Object src,  int  srcPos,
Object dest, int destPos,int length);

2、Arrays.copyOf()不是System的方法,而是Arrays的方法,下面是源码,可以看到本质上是调用的arraycopy方法。,那么其效率必然是比不上 arraycopy的

1

2

3

4

5

6

public static int[] copyOf(int[] original, int newLength) {

int[] copy = new int[newLength];

System.arraycopy(original, 0, copy, 0,

Math.min(original.length, newLength));

return copy;

}

3、clone()的完整定义:protected native Object clone() throws CloneNotSupportedException;

一般用clone效率是最差的,高票答案说的clone()返回的是Object类型,其实是错误的,只有Object[]数组的clone()方法才返回Object类型,子类重写了父类的方法。

来自 <http://www.nowcoder.com/profile/442458/myFollowings/detail/1616900>

 

类加载过程

类从被加载到虚拟机内存中开始,到卸载出内存为止,它的整个生命周期包括:加载(Loading)、验证(Verification)、准备(Preparation)、解析(Resolution)、初始化(Initialization)、使用(Using)和卸载(Unloading)7个阶段。其中准备、验证、解析3个部分统称为连接(Linking)。如图所示。

 

加载、验证、准备、初始化和卸载这5个阶段的顺序是确定的,类的加载过程必须按照这种顺序按部就班地开始,而解析阶段则不一定:它在某些情况下可以在初始化阶段之后再开始,这是为了支持Java语言的运行时绑定(也称为动态绑定或晚期绑定)。以下陈述的内容都已HotSpot为基准。

加载

在加载阶段(可以参考java.lang.ClassLoader的loadClass()方法),虚拟机需要完成以下3件事情:

      1. 通过一个类的全限定名来获取定义此类的二进制字节流(并没有指明要从一个Class文件中获取,可以从其他渠道,譬如:网络、动态生成、数据库等);
      2. 将这个字节流所代表的静态存储结构转化为方法区的运行时数据结构;
      3. 在内存中生成一个代表这个类的java.lang.Class对象,作为方法区这个类的各种数据的访问入口;

加载阶段和连接阶段(Linking)的部分内容(如一部分字节码文件格式验证动作)是交叉进行的,加载阶段尚未完成,连接阶段可能已经开始,但这些夹在加载阶段之中进行的动作,仍然属于连接阶段的内容,这两个阶段的开始时间仍然保持着固定的先后顺序。

验证

验证是连接阶段的第一步,这一阶段的目的是为了确保Class文件的字节流中包含的信息符合当前虚拟机的要求,并且不会危害虚拟机自身的安全。

验证阶段大致会完成4个阶段的检验动作:

      1. 文件格式验证:验证字节流是否符合Class文件格式的规范;例如:是否以魔术0xCAFEBABE开头、主次版本号是否在当前虚拟机的处理范围之内、常量池中的常量是否有不被支持的类型。
      2. 元数据验证:对字节码描述的信息进行语义分析(注意:对比javac编译阶段的语义分析),以保证其描述的信息符合Java语言规范的要求;例如:这个类是否有父类,除了java.lang.Object之外。
      3. 字节码验证:通过数据流和控制流分析,确定程序语义是合法的、符合逻辑的。
      4. 符号引用验证:确保解析动作能正确执行。

验证阶段是非常重要的,但不是必须的,它对程序运行期没有影响,如果所引用的类经过反复验证,那么可以考虑采用-Xverifynone参数来关闭大部分的类验证措施,以缩短虚拟机类加载的时间。

准备

准备阶段是正式为类变量分配内存并设置类变量初始值的阶段,这些变量所使用的内存都将在方法区中进行分配。这时候进行内存分配的仅包括类变量(被static修饰的变量),而不包括实例变量,实例变量将会在对象实例化时随着对象一起分配在堆中。其次,这里所说的初始值“通常情况”下是数据类型的零值,假设一个类变量的定义为:public static int value=123;那变量value在准备阶段过后的初始值为0而不是123.因为这时候尚未开始执行任何java方法,而把value赋值为123的putstatic指令是程序被编译后,存放于类构造器()方法之中,所以把value赋值为123的动作将在初始化阶段才会执行。

至于“特殊情况”是指:public static final int value=123,即当类字段的字段属性是ConstantValue时,会在准备阶段初始化为指定的值,所以标注为final之后,value的值在准备阶段初始化为123而非0.

解析

解析阶段是虚拟机将常量池内的符号引用替换为直接引用的过程。解析动作主要针对类或接口、字段、类方法、接口方法、方法类型、方法句柄和调用点限定符7类符号引用进行。

初始化

类初始化阶段是类加载过程的最后一步,到了初始化阶段,才真正开始执行类中定义的java程序代码。在准备极端,变量已经付过一次系统要求的初始值,而在初始化阶段,则根据程序猿通过程序制定的主管计划去初始化类变量和其他资源,或者说:初始化阶段是执行类构造器<clinit>()方法的过程.

<clinit>()方法是由编译器自动收集类中的所有类变量的赋值动作和静态语句块static{}中的语句合并产生的,编译器收集的顺序是由语句在源文件中出现的顺序所决定的,静态语句块只能访问到定义在静态语句块之前的变量,定义在它之后的变量,在前面的静态语句块可以赋值,但是不能访问

原文链接  http://www.importnew.com/18548.html

来自 <http://www.nowcoder.com/profile/442458/myFollowings/detail/1616941>

 

Java默认提供的三个类加载器:ClassLoader是BootStrap ClassLoader,Extension ClassLoader,App ClassLoader

ClassLoader使用的是双亲委托模型来搜索类的

ClassLoader就是用来动态加载class文件到内存当中用的

一个jvm中默认的classloader有Bootstrap ClassLoader、Extension ClassLoader、App ClassLoader,分别各司其职:

      • Bootstrap ClassLoader     负责加载java基础类,主要是 %JRE_HOME/lib/ 目录下的rt.jar、resources.jar、charsets.jar和class等
      • Extension ClassLoader      负责加载java扩展类,主要是 %JRE_HOME/lib/ext 目录下的jar和class
      • App ClassLoader           负责加载当前java应用的classpath中的所有类。

classloader 加载类用的是全盘负责委托机制。 所谓全盘负责,即是当一个classloader加载一个Class的时候,这个Class所依赖的和引用的所有 Class也由这个classloader负责载入,除非是显式的使用另外一个classloader载入。

所以,当我们自定义的classlo ader加载成功了 com.company.MyClass以后,MyClass里所有依赖的class都由这个classLoader来加载完成。

ClassLoader使用的是 双亲委托模型 来搜索类的,每个ClassLoader实例都有一个父类加载器的引用(不是继承的关系,是一个包含的关系),虚拟机内置的类加载器(Bootstrap ClassLoader)本身没有父类加载器,但可以用作其它ClassLoader实例的的父类加载器。当一个ClassLoader实例需要加载某个类时,它会试图亲自搜索某个类之前,先把这个任务委托给它的父类加载器,这个过程是由上至下依次检查的,首先由最顶层的类加载器Bootstrap ClassLoader试图加载,如果没加载到,则把任务转交给Extension ClassLoader试图加载,如果也没加载到,则转交给App ClassLoader 进行加载,如果它也没有加载得到的话,则返回给委托的发起者,由它到指定的文件系统或网络等URL中加载该类。如果它们都没有加载到这个类时,则抛出ClassNotFoundException异常。否则将这个找到的类生成一个类的定义,并将它加载到内存当中,最后返回这个类在内存中的Class实例对象。

 

来自 <http://www.nowcoder.com/test/question/done?tid=4274744&qid=14508#summary>

 

标识符可以包括这4种字符:字母、下划线、$、数字;开头不能是数字;不能是关键字

来自 <http://www.nowcoder.com/test/question/done?tid=4276011&qid=14976#summary>

 

首先,我们要知道,静态的方法也是可以通过对象.来访问的。

其次,null可以被强制类型转换成任意类型的对象,于是通过它来执行静态方法,

来自 <http://www.nowcoder.com/test/question/done?tid=4276011&qid=25374#summary>

 

ResultSet中记录行的第一列索引为1

在jdbc中操纵sql语句,Statement state=conn.createStatement(); ResultSet result=state.execute(); result.getObject(1),也是从1开始查询。查询数据是从第一行开始开始查询,与普通数组有些区别

来自 <http://www.nowcoder.com/test/question/done?tid=4277633&qid=3223#summary>

 

Statement是sql语句的载体,下面三个是标准的Statement类

      1. Statement是标准的Statement类,通过字符串对sql语句进行拼接,但是它存在sql注入的危险
      2. PreparedStatement对sql语句进行了预编译,可以防止SQL注入
      3. CallableStatement用来调用存储过程的

而BatchedStatement用于批量操作数据库,BatchedStatement不是标准的Statement类

来自 <http://www.nowcoder.com/test/question/done?tid=4277633&qid=1468#summary>

 

getParameter()是获取POST/GET传递的参数值;

getInitParameter获取Tomcat的server.xml中设置Context的初始化参数

getAttribute()是获取对象容器中的数据值;

getRequestDispatcher是请求转发。

来自 <http://www.nowcoder.com/test/question/done?tid=4282495&qid=15047#summary>

 

Thread可以被继承,用于创建新的线程

Number类可以被继承,Integer,Float,Double等都继承自Number类

Double类的声明为:public final class Doubleextends Numberimplements Comparable<Double>, final生明的类不能被继承

Math类的声明为:public final class Mathextends Object ,不能被继承

ClassLoader可以被继承,用户可以自定义类加载器

来自 <http://www.nowcoder.com/test/question/done?tid=4283368&qid=15313#summary>

 

CallableStatement继承自PreparedSatement,PreparedStatement继承自Statement。

来自 <http://www.nowcoder.com/test/question/done?tid=4284596&qid=22472#summary>

 

<<表示左移位

>>表示带符号右移位

>>>表示无符号右移

但是没有<<<运算符!!!

来自 <http://www.nowcoder.com/test/question/done?tid=4297984&qid=3660#summary>

 

java.io.Reader是一个读取字符流的抽象类,通过继承Reader类,可以很方便的读取字符流,比如,我们可以将一个字符串读取为一串串(字符)流,还可以读取一个文件里的内容为一串串的流。

Java(1.6.x)里提供了几种Reader的直接继承类,具体的有:BufferedReader, CharArrayReader, FileReader, InputStreamReader, PipedReader, StringReader等,子类须实现的方法只有 read(char[], int, int) 和 close()。

来自 <http://www.nowcoder.com/test/question/done?tid=4297984&qid=3662#summary>

 

Ant和Maven都是基于Java的构建(build)工具。理论上来说,有些类似于(Unix)C中的make ,但没有make的缺陷。Ant是软件构建工具,Maven的定位是软件项目管理和理解工具。

Ant特点 ›

没有一个约定的目录结构 ›必须明确让ant做什么,什么时候做,然后编译,打包 。没有生命周期,必须定义目标及其实现的任务序列,没有集成依赖管理,Ant构建文件默认命名为build.xml

Maven特点

拥有约定,知道你的代码在哪里,放到哪里去 ›拥有一个生命周期,例如执行 mvn install 就可以自动执行编译,测试,打包等构建过程,只需要定义一个pom.xml,然后把源码放到默认的目录,Maven帮你处理其他事情,拥有依赖管理,仓库管理。Maven默认构建文件为pom.xml

来自 <http://www.nowcoder.com/test/question/done?tid=4297984&qid=14938#summary>

 

会话跟踪是一种灵活、轻便的机制,它使Web上的状态编程变为可能。

HTTP是一种无状态协议,每当用户发出请求时,服务器就会做出响应,客户端与服务器之间的联系是离散的、非连续的。当用户在同一网站的多个页面之间转换时,根本无法确定是否是同一个客户,会话跟踪技术就可以解决这个问题。当一个客户在多个页面间切换时,服务器会保存该用户的信息。

有四种方法可以实现会话跟踪技术:URL重写、隐藏表单域、Cookie、Session。

1)隐藏表单域:<input type=”hidden”>,非常适合步需要大量数据存储的会话应用。

2)URL 重写:URL 可以在后面附加参数,和服务器的请求一起发送,这些参数为名字/值对。

3)Cookie:一个 Cookie 是一个小的,已命名数据元素。服务器使用 SET-Cookie 头标将它作为 HTTP

响应的一部分传送到客户端,客户端被请求保存 Cookie 值,在对同一服务器的后续请求使用一个

Cookie 头标将之返回到服务器。与其它技术比较,Cookie 的一个优点是在浏览器会话结束后,甚至

在客户端计算机重启后它仍可以保留其值。

4)Session:使用 setAttribute(String str,Object obj)方法将对象捆绑到一个会话。

来自 <http://www.nowcoder.com/test/question/done?tid=4303047&qid=15245#summary>

 

 

1、ThreadLocal的类声明:

public class ThreadLocal<T>

可以看出ThreadLocal并没有继承自Thread,也没有实现Runnable接口。

2、ThreadLocal类为每一个线程都维护了自己独有的变量拷贝。每个线程都拥有了自己独立的一个变量。

所以ThreadLocal重要作用并不在于多线程间的数据共享,而是数据的独立。

由于每个线程在访问该变量时,读取和修改的,都是自己独有的那一份变量拷贝,不会被其他线程访问,

变量被彻底封闭在每个访问的线程中。

3、ThreadLocal中定义了一个哈希表用于为每个线程都提供一个变量的副本:

static class ThreadLocalMap {

static class Entry extends WeakReference<ThreadLocal> {

/** The value associated with this ThreadLocal. */

Object value;

Entry(ThreadLocal k, Object v) {

super(k);

value = v;

}

}

/**

* The table, resized as necessary.

* table.length MUST always be a power of two.

*/

private Entry[] table;

}

来自 <http://www.nowcoder.com/test/question/done?tid=4303737&qid=7691#summary>

 

关于HashMap:源码程序中用到了一个重要的内部接口:Map.Entry,每个 Map.Entry 其实就是一个 key-value 对。当系统决定存储 HashMap 中的 key-value 对时,完全没有考虑 Entry 中的 value,仅仅只是根据 key 来计算并决定每个 Entry 的存储位置。Entry是数组,数组中的每个元素上挂这个一条链表。。

链表法就是将相同hash值的对象组织成一个链表放在hash值对应的槽位;开放地址法是通过一个探测算法,当某个槽位已经被占据的情况下继续查找下一个可以使用的槽位。很显然我们使用的不是开放地址法。hashmap采用拉链法解决冲突

来自 <http://www.nowcoder.com/test/question/done?tid=4304544&qid=14935#summary>

 

方法区在JVM中也是一个非常重要的区域,它与堆一样,是被 线程共享 的区域。 在方法区中,存储了每个类的信息(包括类的名称、方法信息、字段信息)、静态变量、常量以及编译器编译后的代码等。

大多数 JVM 将内存区域划分为 Method AreaNon-Heap)(方法区) ,Heap(堆) , Program Counter Register(程序计数器) ,   VM Stack(虚拟机栈,也有翻译成JAVA 方法栈的),Native Method Stack  ( 本地方法栈 ),其中Method Area 和 Heap 是线程共享的  ,VM StackNative Method Stack  和Program Counter Register  是非线程共享的。为什么分为 线程共享和非线程共享的呢?请继续往下看。

首先我们熟悉一下一个一般性的 Java 程序的工作过程。一个 Java 源程序文件,会被编译为字节码文件(以 class 为扩展名),每个java程序都需要运行在自己的JVM上,然后告知 JVM 程序的运行入口,再被 JVM 通过字节码解释器加载运行。那么程序开始运行后,都是如何涉及到各内存区域的呢?

概括地说来,JVM初始运行的时候都会分配好 Method Area(方法区) 和Heap(堆) ,而JVM 每遇到一个线程,就为其分配一个 Program Counter Register(程序计数器) ,   VM Stack(虚拟机栈)和Native Method Stack  (本地方法栈), 当线程终止时,三者(虚拟机栈,本地方法栈和程序计数器)所占用的内存空间也会被释放掉。这也是为什么我把内存区域分为线程共享和非线程共享的原因,非线程共享的那三个区域的生命周期与所属线程相同,而线程共享的区域与JAVA程序运行的生命周期相同,所以这也是系统垃圾回收的场所只发生在线程共享的区域(实际上对大部分虚拟机来说知发生在Heap上)的原因。

来自 <http://www.nowcoder.com/test/question/done?tid=4371423&qid=14817#summary>

 

JDK提供的用于并发编程的同步器有哪些?

1、Java 并发库 的Semaphore 可以很轻松完成信号量控制,Semaphore可以控制某个资源可被同时访问的个数,通过 acquire() 获取一个许可,如果没有就等待,而 release() 释放一个许可。

2、CyclicBarrier 主要的方法就是一个:await()。await() 方法没被调用一次,计数便会减少1,并阻塞住当前线程。当计数减至0时,阻塞解除,所有在此 CyclicBarrier 上面阻塞的线程开始运行。

3、直译过来就是倒计数(CountDown)门闩(Latch)。倒计数不用说,门闩的意思顾名思义就是阻止前进。在这里就是指 CountDownLatch.await() 方法在倒计数为0之前会阻塞当前线程。

(Counter不是并发编程的同步器)

同步器是一些使线程能够等待另一个线程的对象,允许它们协调动作。最常用的同步器是CountDownLatch和Semaphore,不常用的是Barrier 和Exchanger

来自 <http://www.nowcoder.com/test/question/done?tid=4371423&qid=7696#summary>

 

javax.servlet 包中包含了 7 个接口 ,3 个类和 2 个异常类 , 它们分别是 :

接口 :RequestDispatcher,Servlet,ServletConfig,ServletContext,ServletRequest,ServletResponse 和

SingleThreadModel

类 :GenericServlet,ServletInputStream 和 ServletOutputStream

异常类 :ServletException 和 UnavailableException

来自 <http://www.nowcoder.com/test/question/done?tid=4372199&qid=15034#summary>

 

getSession(boolean create)意思是返回当前reqeust中的HttpSession ,如果当前reqeust中的HttpSession 为null,当create为true,就创建一个新的Session,否则返回null;

简而言之:

HttpServletRequest.getSession(ture) 等同于 HttpServletRequest.getSession()

HttpServletRequest.getSession(false) 等同于 如果当前Session没有就为null;

来自 <http://blog.csdn.net/xxd851116/article/details/4296866>

 

计算余弦值使用Math类的cos()方法,而Math.cos()里面的参数需要的是弧度

toRadians()是将角度转换为弧度

toDegrees()是将弧度转换为角度

来自 <http://www.nowcoder.com/test/question/done?tid=4383229&qid=2298#summary>

 

数据库操作中,为了有效保证并发读取数据的正确性,提出的事务隔离级别;为了解决更新丢失,脏读,不可重读(包括虚读和幻读)等问题在标准SQL规范中,定义了4个事务隔离级别,分别为未授权读取,也称为读未提交(read uncommitted);授权读取,也称为读提交(read committed);可重复读取(repeatable read);序列化(serializable.

数据库事务的隔离级别有4个,由低到高依次为Read uncommitted、Read committed、Repeatable read、Serializable,这四个级别可以逐个解决脏读、不可重复读、幻读这几类问题。

√: 可能出现    ×: 不会出现

脏读 不可重复读 幻读
Read uncommitted
Read committed ×
Repeatable read × ×
Serializable × × ×

来自 <http://www.nowcoder.com/test/question/done?tid=4384937&qid=15546#summary>

 

float x 与“零值”比较的if语句为?

if (fabs(x) < 0.00001f)

不可将浮点变量用“==”或“!=”与任何数字比较。

千万要留意,无论是float还是double类型的变量,都有精度限制。所以一定要避免将浮点变量用“==”或“!=”与数字比较,应该设法转化成“>=”或“<=”形式。

假设浮点变量的名字为x,应当将 if (x == 0.0) 转化为   if ((x>=-EPSINON) && (x<=EPSINON))

或者 if ( fabs(x) <=EPSINON)  // fabs(x)取x的绝对值

其中EPSINON是允许的误差(即精度)。

参考: http://blog.csdn.net/azhang00000/article/details/5357134

来自 <http://www.nowcoder.com/test/question/done?tid=4389843&qid=14321>

 

java不完全算是编译型语言,他编译的字节码文件运行时是解释执行的,其次,java和C++的类也不都完全是静态绑定的,比如C+++的虚函数,java的父类引用子类对象等情况。

java也可以数组溢出,溢出是会抛出异常,也就是ArrayIndexOutOfBoundsException

来自 <http://www.nowcoder.com/questionTerminal/b6f55c8749764ed2876f76a84c4c46a4>

 

ServletConfig接口默认是哪里实现的? GenericServlet

GenericServlet类的实现接口中包括了ServletConfig接口,但是它自身的init(ServletConfig config)方法又需要外界给它传递一个实现ServletConfig的对象,就是说GenericServlet和ServletConfig的依赖关系既是继承关系,也是一种关联关系。

public abstract class GenericServlet

extends java.lang.Object

implements Servlet, ServletConfig, java.io.Serializable

从Servlet 的API文档上面可以看到上面一段,

抽象类GenericServlet实现了Servlet, ServletConfig等接口。

 

public abstract class HttpServlet extends GenericServlet

implements java.io.Serializable

抽象类HttpServlet 继承自GenericServlet

来自 <http://www.nowcoder.com/test/question/done?tid=4404451&qid=15045#summary>

 

‘*’,’/’,’+’操作符都可用于float和double

只有%取余操作,只适用于整型

来自 <http://www.nowcoder.com/test/question/done?tid=4405649&qid=3215#summary>

 

Webservice是跨平台,跨语言的远程调用技术

Webservice通信机制实质就是xml数据交换

Webservice采用了soap协议(简单对象协议)进行通信

WSDL是用于描述 Web Services 以及如何对它们进行访问

WSDL 指网络服务描述语言 (Web Services Description Language)。

WSDL 是一种使用 XML 编写的文档。这种文档可描述某个 Web service。它可规定服务的位置,以及此服务提供的操作(或方法)

来自 <http://www.nowcoder.com/test/question/done?tid=4405649&qid=15076#summary>

images

发表评论

电子邮件地址不会被公开。 必填项已用*标注