Java面试题-基础篇二(干货)

十一、是否能够从一个static方法内部发出对非static方法的调用?java

        不能够。由于非static方法是要与对象关联在一块儿的,必须建立一个对象后,才能够在该对象上进行方法调用,而static方法调用时不须要建立对象,能够直接调用。也就是说,当一个static方法被调用时,可能尚未建立任何实例对象,若是从一个static方法中发出对非static方法的调用,那个非static方法是关联到哪一个对象上的呢?这个逻辑没法成立,因此,一个static方法内部发出对非static方法的调用。web

 

十二、Integer与int的区别算法

        int是java提供的8种原始数据类型之一。Java为每一个原始类型提供了封装类,Integer是java为int提供的封装类。int的默认值为0,而Integer的默认值为null,即Integer能够区分出未赋值和值为0的区别,int则没法表达出未赋值的状况。编程

        例如:要想表达出没有参加考试和考试成绩为0的区别,则只能使用Integer。在JSP开发中,Integer的默认为null,因此用el表达式在文本框中显示时,值为空白字符串,而int默认的默认值为0,因此用el表达式在文本框中显示时,结果为0,因此,int不适合做为web层的表单数据的类型。windows

        在Hibernate中,若是将OID定义为Integer类型,那么Hibernate就能够根据其值是否为null而判断一个对象是不是临时的,若是将OID定义为了int类型,还须要在hbm映射文件中设置其unsaved-value属性为0。api

        另外,Integer提供了多个与整数相关的操做方法,例如,将一个字符串转换成整数,Integer中还定义了表示整数的最大值和最小值的常量。多线程

 

1三、Math.round(11.5)等於多少?Math.round(-11.5)等於多少?并发

        Math类中提供了三个与取整有关的方法:ceil、floor、round,这些方法的做用与它们的英文名称的含义相对应。eclipse

        例如,ceil的英文意义是天花板,该方法就表示向上取整,Math.ceil(11.3)的结果为12,Math.ceil(-11.3)的结果是-11;floor的英文意义是地板,该方法就表示向下取整,Math.ceil(11.6)的结果为11,Math.ceil(-11.6)的结果是-12;最难掌握的是round方法,它表示“四舍五入”,算法为Math.floor(x+0.5),即将原来的数字加上0.5后再向下取整,因此,Math.round(11.5)的结果为12,Math.round(-11.5)的结果为-11。编程语言

这里有一些笔误,floor的英文意义是地板,该方法就表示向下取整,Math.floor(11.6)的结果为11,Math.floor(-11.6)的结果是-12;

 

1四、Overload和Override的区别?Overloaded的方法是否能够改变返回值的类型?

        Overload是重载的意思,Override是覆盖的意思,也就是重写。

        重载Overload表示同一个类中能够有多个名称相同的方法,但这些方法的参数列表各不相同(即参数个数或类型不一样)。

        重写Override表示子类中的方法能够与父类中的某个方法的名称和参数彻底相同,经过子类建立的实例对象调用这个方法时,将调用子类中的定义方法,这至关于把父类中定义的那个彻底相同的方法给覆盖了,这也是面向对象编程的多态性的一种表现。子类覆盖父类的方法时,只能比父类抛出更少的异常,或者是抛出父类抛出的异常的子异常,由于子类能够解决父类的一些问题,不能比父类有更多的问题。子类方法的访问权限只能比父类的更大,不能更小。若是父类的方法是private类型,那么,子类则不存在覆盖的限制,至关于子类中增长了一个全新的方法。

        至于Overloaded的方法是否能够改变返回值的类型这个问题,要看你倒底想问什么呢?这个题目很模糊。若是几个Overloaded的方法的参数列表不同,它们的返回者类型固然也能够不同。但我估计你想问的问题是:若是两个方法的参数列表彻底同样,是否可让它们的返回值不一样来实现重载Overload。这是不行的,咱们能够用反证法来讲明这个问题,由于咱们有时候调用一个方法时也能够不定义返回结果变量,即不要关心其返回结果,例如,咱们调用map.remove(key)方法时,虽然remove方法有返回值,可是咱们一般都不会定义接收返回结果的变量,这时候假设该类中有两个名称和参数列表彻底相同的方法,仅仅是返回类型不一样,java就没法肯定编程者倒底是想调用哪一个方法了,由于它没法经过返回结果类型来判断。

        override能够翻译为覆盖,从字面就能够知道,它是覆盖了一个方法而且对其重写,以求达到不一样的做用。对咱们来讲最熟悉的覆盖就是对接口方法的实现,在接口中通常只是对方法进行了声明,而咱们在实现时,就须要实现接口声明的全部方法。除了这个典型的用法之外,咱们在继承中也可能会在子类覆盖父类中的方法。在覆盖要注意如下的几点:

        一、覆盖的方法的标志必需要和被覆盖的方法的标志彻底匹配,才能达到覆盖的效果;

        二、覆盖的方法的返回值必须和被覆盖的方法的返回一致;

        三、覆盖的方法所抛出的异常必须和被覆盖方法的所抛出的异常一致,或者是其子类;

        四、被覆盖的方法不能为private,不然在其子类中只是新定义了一个方法,并无对其进行覆盖。

        Overload对咱们来讲可能比较熟悉,能够翻译为重载,它是指咱们能够定义一些名称相同的方法,经过定义不一样的输入参数来区分这些方法,而后再调用时,VM就会根据不一样的参数样式,来选择合适的方法执行。在使用重载要注意如下的几点:

        一、在使用重载时只能经过不一样的参数样式。例如,不一样的参数类型,不一样的参数个数,不一样的参数顺序(固然,同一方法内的几个参数类型必须不同,例如能够是fun(int,float),可是不能为fun(int,int));

        二、不能经过访问权限、返回类型、抛出的异常进行重载;

        三、方法的异常类型和数目不会对重载形成影响;

        四、对于继承来讲,若是某一方法在父类中是访问权限是priavte,那么就不能在子类对其进行重载,若是定义的话,也只是定义了一个新方法,而不会达到重载的效果。

 

1五、接口是否可继承接口?抽象类是否可实现(implements)接口?抽象类是否可继承具体类(concreteclass)?抽象类中是否能够有静态的main方法?

        接口能够继承接口。抽象类能够实现(implements)接口,抽象类能够继承具体类。抽象类中能够有静态的main方法。

        备注:只要明白了接口和抽象类的本质和做用,这些问题都很好回答,你想一想,若是你是java语言的设计者,你是否会提供这样的支持,若是不提供的话,有什么理由吗?若是你没有道理不提供,那答案就是确定的了。

        只要记住抽象类与普通类的惟一区别就是不能建立实例对象和容许有abstract方法。

 

1六、Java中实现多态的机制是什么?

        靠的是父类或接口定义的引用变量能够指向子类或具体实现类的实例对象,而程序调用的方法在运行期才动态绑定,就是引用变量所指向的具体实例对象的方法,也就是内存里正在运行的那个对象的方法,而不是引用变量的类型中定义的方法。

 

1七、abstractclass和interface语法上有什么区别?

 

1.抽象类能够有构造方法,接口中不能有构造方法。

2.抽象类中能够有普通成员变量,接口中没有普通成员变量

3.抽象类中能够包含非抽象的普通方法,接口中的全部方法必须都是抽象的,不能有非抽象的普通方法。

4. 抽象类中的抽象方法的访问类型能够是public,protected和(默认类型,虽然

eclipse下不报错,但应该也不行),但接口中的抽象方法只能是public类型的,而且默认即为public abstract类型。

5. 抽象类中能够包含静态方法,接口中不能包含静态方法

6. 抽象类和接口中均可以包含静态成员变量,抽象类中的静态成员变量的访问类型能够任意,但接口中定义的变量只能是publicstatic final类型,而且默认即为publicstatic final类型。

7. 一个类能够实现多个接口,但只能继承一个抽象类。

 

1八、abstract的method是否可同时是static,是否可同时是native,是否可同时是synchronized?

        abstract的method不能够是static的,由于抽象的方法是要被子类实现的,而static与子类扯不上关系!

        native方法表示该方法要用另一种依赖平台的编程语言实现的,不存在着被子类实现的问题,因此,它也不能是抽象的,不能与abstract混用。例如,FileOutputSteam类要硬件打交道,底层的实现用的是操做系统相关的api实现;例如,在windows用c语言实现的,因此,查看jdk的源代码,能够发现FileOutputStream的open方法的定义以下:

private native void open(Stringname) throwsFileNotFoundException;

        若是咱们要用java调用别人写的c语言函数,咱们是没法直接调用的,咱们须要按照java的要求写一个c语言的函数,又咱们的这个c语言函数去调用别人的c语言函数。因为咱们的c语言函数是按java的要求来写的,咱们这个c语言函数就能够与java对接上,java那边的对接方式就是定义出与咱们这个c函数相对应的方法,java中对应的方法不须要写具体的代码,但须要在前面声明native。

        关于synchronized与abstract合用的问题,我以为也不行,由于在我几年的学习和开发中,历来没见到过这种状况,而且我以为synchronized应该是做用在一个具体的方法上才有意义。并且,方法上的synchronized同步所使用的同步锁对象是this,而抽象方法上没法肯定this是什么。

 

1九、内部类能够引用它的包含类的成员吗?有没有什么限制?

        彻底能够。若是不是静态内部类,那没有什么限制!

        若是你把静态嵌套类看成内部类的一种特例,那在这种状况下不能够访问外部类的普通成员变量,而只能访问外部类中的静态成员,例如,下面的代码:

class Outer

{

static int x;

static class Inner

    {

        voidtest()

        {

              syso(x);

        }

    }

}

 

20、String s = "Hello";s = s + "world!";这两行代码执行后,原始的String对象中的内容到底变了没有?

        没有。由于String被设计成不可变(immutable)类,因此它的全部对象都是不可变对象。在这段代码中,s原先指向一个String对象,内容是 "Hello",而后咱们对s进行了+操做,那么s所指向的那个对象是否发生了改变呢?答案是没有。这时,s不指向原来那个对象了,而指向了另外一个 String对象,内容为"Hello world!",原来那个对象还存在于内存之中,只是s这个引用变量再也不指向它了。

        经过上面的说明,咱们很容易导出另外一个结论,若是常常对字符串进行各类各样的修改,或者说,不可预见的修改,那么使用String来表明字符串的话会引发很大的内存开销。由于String对象创建以后不能再改变,因此对于每个不一样的字符串,都须要一个String对象来表示。这时,应该考虑使用StringBuffer类,它容许修改,而不是每一个不一样的字符串都要生成一个新的对象。而且,这两种类的对象转换十分容易。
        同时,咱们还能够知道,若是要使用内容相同的字符串,没必要每次都new一个String。例如咱们要在构造器中对一个名叫s的String引用变量进行初始化,把它设置为初始值,应当这样作:
public class Demo {
private String s;
...
public Demo {
s = "Initial Value";
}
...
}

而非
s = new String("Initial Value");后者每次都会调用构造器,生成新对象,性能低下且内存开销大,而且没有意义,由于String对象不可改变,因此对于内容相同的字符串,只要一个String对象来表示就能够了。也就说,屡次调用上面的构造器建立多个对象,他们的            String类型属性s都指向同一个对象。上面的结论还基于这样一个事实:对于字符串常量,若是内容相同,Java认为它们表明同一个String对象。而用关键字new调用构造器,老是会建立一个新的对象,不管内容是否相同。        至于为何要把String类设计成不可变类,是它的用途决定的。其实不仅String,不少Java标准类库中的类都是不可变的。在开发一个系统的时候,咱们有时候也须要设计不可变类,来传递一组相关的值,这也是面向对象思想的体现。不可变类有一些优势,好比由于它的对象是只读的,因此多线程并发访问也不会有任何问题。固然也有一些缺点,好比每一个不一样的状态都要一个对象来表明,可能会形成性能上的问题。因此Java标准类库还提供了一个可变版本,即StringBuffer。

相关文章
相关标签/搜索