Java面试题

冰封百度

持续整理中...

          类和对象            

1.下面哪个不是Object类所定义的public method?( )
A.finalize() B.clone() C.wait() C.sleep()

          JVM            

1.下面给出的Java中ClassLoader的描述,哪些是正确的?( )
A.ClassLoader没有层次关系
B.所有类中的ClassLoader都是AppClassLoader
C.通过Class.forName(String className)能够动态加载一个类
D.不同的ClassLoader加载同一个Class文件,所得的类是相同的

2.Which characters does JVM use?(JVM使用哪种字符编码格式?)( )
A.ASCII characters  B.Unicode characters
C.Cp1252      D.UTF-8

          i++            

1.以下代码的执行结果是____

public static void main(String[] args) {
    int i = 0;
    int x = i++;
    int y = ++i;
    int z = i++ + ++i;
    System.out.println(x);
    System.out.println(y);
    System.out.println(z);
}

2.下列程序的输出结果是( )

public static void main(String[] args) {
    int j = 0;
    for (int i = 0; i < 100; i++) {
        j = j++;
    }
    System.out.println(j);
}

A.0  B.99  C.100  D.101

3.下列程序的输出结果是( )

public static void main(String[] args) {
    int a = 5, b = 3;
    if(!(a == b) && (a == 1 + b++)){};
    System.out.println(a + "," + b);
}

A.5,3  B.0,1  C.0,3  D.5,4

4.以下代码的执行结果是____

public static void main(String[] args) {
    int i = 0;
    i = i++ + ++i;
    int j = 0;
    j = ++j + j++ + j++ + j++;
    int  k = 0;
    k = k++ + k++ + k++ + ++k;
    int h = 0;
    h = ++h + ++h;
    int p1 = 0, p2 = 0, q1 = 0, q2 = 0;
    q1 = ++p1;
    q2 = p2++;
    System.out.println(i);
    System.out.println(j);
    System.out.println(k);
    System.out.println(h);
    System.out.println(p1);
    System.out.println(p2);
    System.out.println(q1);
    System.out.println(q2);
}

5.以下代码的执行结果是____

public static void main(String[] args) {
    int m = 5, n = 5;
    if((m != 5) && (n++ == 5)){}
    System.out.println(n);
    
    m = n = 5;
    if((m != 5) & (n++ == 6)){}
    System.out.println(n);
    
    m = n = 5;
    if((m == 5) || (n++ == 5)){}
    System.out.println(n);
    
    m = n = 5;
    if((m == 5) | (n++ == 6)){}
    System.out.println(n);
    
    int a = 1, b =2;
    int c = a & b;
    System.out.println(c);
}

          类型转换            

1.Which of the following will compile correctly(下列哪项编译正确?)( )
A.Short myshort = 99S;  B.float z = 1.0  C.int t = "abc".length()  D.char c = 17c;

2.下面代码的输出结果是( )

public static void main(String[] args) {
    public static void main(String[] args){
    int i = 012;
    int j = 034;
    int k = (int)056L;
    int l = 078;
    System.out.println(i);
    System.out.println(j);
    System.out.println(k);
}

A.输出12,34,56  B.输出10,28,46
C.int k = (int)056L;行编译错误  D.int l = (int)078;行编译错误

3.以下程序错误的是( )
A.short s=1;s=s+1;  B.short s=1;s+=1;

4.下面代码的输出结果是( )

public static void main(String[] args) {
    char x = 'x';
    int i = 10;
    System.out.println(false ? i : x);
    System.out.println(false ? 10 : x);
}

A.120 x  B.120 120  C.x 120  D.以上答案都不对

          程序结构            

1.Which declaration of the main() method in a stand-alone program are NOT valid?( )
(哪一个Main方法的声明在独立程序中是无效的?)
A.public static void main()
B.public static void main(String[] string)
C.public static void main(String[] exp) throws FileNotFondException
D.Static void main(String args)

2.以下程序的输出结果是?( )

public class Penguin {

    private String name = null;
    private int health = 0;
    private String sex = null;
    
    public void Penguin() {
        health = 10;
        sex = "雄";
        System.out.println("执行构造方法。");
    }
    
    public void print(){
        System.out.println("企鹅的名字是" + name + ",健康值是" + health + ",性别是" + sex + "。");
    }
    
    public static void main(String[] args) {
        Penguin pgn = new Penguin();
        pgn.print();
    }

}

A.企鹅的名字是null,健康值是10,性别是雄。
B.执行构造方法。
企鹅的名字是null,健康值是0,性别是null。
C.企鹅的名字是null,健康值是0,性别是null。
D.执行构造方法。
企鹅的名字是null,健康值是10,性别是雄。

          运算符            

1.以下代码的输出结果是( )

public static void main(String[] args) {
    boolean b = true ? false : true == true ? false : true;
    System.out.println(b);
}

A.true  B.false  C.null  D.以上答案都不对

2.以下代码的输出结果是( )

public static void main(String[] args) {
    int i = 42;
    String s = (i < 40) ? "life" : (i > 50) ? "universe" : "everything";
    System.out.println(s);
}

A.life  B.universe  C.everything  D.以上答案都不对

3.以下代码的输出结果是( )

public static void main(String[] args) {
    int a = 5;
    System.out.println(a < 5 ? 10.9 : 9);
}

A.编译错误  B.10.9  C.9  D.以上答案都不对

4.以下代码的输出结果是____

public static void main(String[] args) {
    int a = 1;
    int b = 2;
    System.out.println(a & b);
    System.out.println(a | b);
}

5.以下代码的输出结果是____

public static void main(String[] args) {
    int a = 1;
    int b = 2;
    System.out.println(b << a);
    System.out.println(b >> a);
}

6.以下代码的输出结果是____

public static void main(String[] args) {
    int a = 1;
    int b = 2;
    System.out.println(b << a << a);
    System.out.println(b >> a >> a);
    System.out.println(b >> 32);
    System.out.println(b << 33);
}

          算法            

1.编程,输出数组里的全部数值。(假设int[] array = new int[]{1, 2, 3, 4})

2.编程,输出99乘法口诀表

3.编程,输出字符串中出现次数最多的字符,如果有多个则都输出。(假设字符串String str = "abcdefaaaccc"。);

4.编程,有一个整数n,写一个函数f(n),返回0~n之间出现“1”的个数。比如f(1)=1,f(13)=6(1、10、11、12、13)

5.编程,获取斐波那契数列的第n项值。
(斐波那契数列指的是这样一个数列:1、1、2、3、5、8、13、21……这个数列从第3项开始,每一项都等于前两项之和。F[n]=F[n-1]+F[n-2] (n>2,F[1]=1,F[2]=1,F[3]=2,F[4]=3))

          答案          

                  类和对象          


1.下面哪个不是Object类所定义的public method? 答案:
这题看起来很简单,但是仔细一想没那么容易。
Object类定义的公用方法有以下7种:

toString();    //
equals(Object object);
getClass();
hashCode();
wait();
notify();
notifyAll();

wait();方法有三种重载方法
wait(long timeout);
wait(long timeout, int nanos);
再加两个一共是9种public方法。
所以这题的正确答案是A、B、D, 四个选项里只有wait()是公用方法
clone()和finalize()是protected方法。sleep()不是Object类的方法。
《Java程序员面试宝典》给的答案是D,显然错了。
                  JVM          


1.答案:
A.选项错误,ClassLoader具备层次关系。
B.选项错误,ClassLoader不止一种。
D.选项错误,ClassLoader具备层次关系。
正确答案:C

2.答案:
JVM的设计者为了解决编码问题实现Java的跨平台,没有使用任何特定的编码格式,而是使用Unicode(万国码)字符集来表示字符。
所以正确答案是B。

                  i++          


1.答案:
0
2
6

2.答案:
j=j++;//这一步j等于0,循环100次依然是0。
所以正确答案是A。

3.答案:
!(a == b)为true,还需执行后面的(a == 1 + b++),执行后a,b的值分别为5,4。
所以正确答案是D

4.答案:

public static void main(String[] args) {
    int i = 0;
    i = i++ + ++i;    //0 + (1 + 1) = 2
    int j = 0;
    j = ++j + j++ + j++ + j++;    //(1 + 0) + 1 + 2 + 3 = 7
    int  k = 0;
    k = k++ + k++ + k++ + ++k;    //0 + 1 + 2 + (1 + 3) = 7
    int h = 0;
    h = ++h + ++h;    //(1 + 0) + (1 + 1) = 3
    int p1 = 0, p2 = 0, q1 = 0, q2 = 0;
    q1 = ++p1;    //q1 = 1, p1 = 1
    q2 = p2++;    //q2 = 0, p2 = 1
    System.out.println(i);    //2
    System.out.println(j);    //7
    System.out.println(k);    //7
    System.out.println(h);    //3
    System.out.println(p1);    //1
    System.out.println(p2);    //1
    System.out.println(q1);    //1
    System.out.println(q2);    //0
}

5.答案:

public static void main(String[] args) {
    int m = 5, n = 5;
    if((m != 5) && (n++ == 5)){}
    System.out.println(n);    //5
    
    m = n = 5;
    if((m != 5) & (n++ == 6)){}
    System.out.println(n);    //6
    
    m = n = 5;
    if((m == 5) || (n++ == 5)){}
    System.out.println(n);    //5
    
    m = n = 5;
    if((m == 5) | (n++ == 6)){}
    System.out.println(n);    //6
    
    int a = 1, b =2;
    int c = a & b;
    System.out.println(c);    //0
}

所以正确答案是:
5
6
5
6
0

                  类型转换          


1.答案:
A选项错误。short类型赋值时不需要在数值后加s,加s会报错。
B选项错误。float类型赋值时需要在数值后加f,不加f默认会转成double类型,编译报错“不能从double转换为float”。
D选项错误。char类型赋值时不需要在后面加c,加c会报错。
正确答案为C。

2.答案:
在java中以0开头的数字代表8进制,数字范围0~7,以0x开头的数字代表16进制数字范围0~F。

public static void main(String[] args) {
    public static void main(String[] args){
    int i = 012;    //(1x8) + 2 = 10
    int j = 034;    //(3x8) + 4 = 28
    int k = (int)056L;//(5x8) + 6 = 46
    int l = 078;    //编译报错“类型 int 的文字 078 超出了范围”
    System.out.println(i);
    System.out.println(j);
    System.out.println(k);
}

所以正确答案是D

3.答案:
short s=1;s=s+1; //s+1为int型,编译报错“类型不匹配:不能从 int 转换为 short”
short s=1;s+=1; //编译正常
所以正确答案是A。

4.答案:
在Java中,整型、实型、字符型被视为简单数据类型,简单数据类型之间会转换,这些类型由低级到高级分别为:
(byte short char) int long float double (7种 不包括boolean)
简单数据类型之间的转换又可以分为:
(1)低级到高级的自动类型转换。
(2)高级到低级的强制类型转换。
(1)包装类型过渡类型能够转换。

注意表达式中的精度转换。当表达式中有高精度和低精度类型同时存在时,低精度类型会自动转换为高精度类型,输出结果会发生变化,这点要特别注意。

false?i:x中i是整型,x是字符型,整型比字符型的精度高,所以x会自动转换为整型。结果为120
false?10:x中10是整型, 但是是常量表达式。Java编程规范中提到:当后两个表达式有一个是常量表达式时(10),两外一个类型是T(char),而常量表达式可以被T表示时,输出结果是T类型(char类型可以被int表示,所以输出结果依然是char类型)。结果为x
所以正确答案是A.120 x

                  程序结构          


1.答案:
java中对于main方法有严格的定义,必须是
public static void main(String[] x)或
public static void main(String x[])形式的。
修饰符必须是public static,返回类型必须是void(不需要返回类型),参数必须是String[] 不能没有参数也不能是其他参数。
标准格式如下:
public static void main(String[] args){}或
public static void main(String args[]){}
可以修改参数的名字或添加抛出异常。基本是死记硬背的一种格式,遇到此类问题可以和标准格式进行比对。
实际上不写public或参数并不会在编译期间报错但会在运行时报错。
所以这道题不简单,坑挺深的,编译期间4个选项的写法都不会报错,但运行时A、D都会出错。
A、D选项会在运行时报出找不到main方法的错误:
“错误:在类 Test 中找不到 main 方法,请将 main 方法定义为
public static void main(String[] args) 否则 JavaFX 应用程序类必须扩展javafx.application.Application”
所以正确答案是A、D。 如果只能选一个选项的话,选D,《Java程序员面试宝典》一书中给的答案是D,如果恰好考官出的是此书中的题,那就中了。

2.答案:
这道题看起来很简单,如果你选D就错了。
这题考验的是你对构造方法的理解。
构造方法的定义是:与类名完全相同。没有返回值,也不能用void来修饰。
注意的是无返回类型而不是void返回类型。
在java中普通方法可以和构造方法同名,但是必须带有返回值。
实际上这题由于public void Penguin(){}方法写了void返回类型,所以他没有符合构造方法的条件,而是被当作普通方法了。程序执行了默认的构造方法并没有执行public void Penguin{}这个方法,变量没有被初始化,所以结果是C。

                  运算符          


1.答案:
a?b:c;是三目运算符,相当于:

if(a){
    b;
}else{
    c;
}

boolean b = true ? false : true == true ? false : true;相当于:
boolean b = true ? false : (true == true ? false : true);相当于:

boolean b;
if(true){
    b = false;
}else{
    if(true == true){
        b = false;
    }else{
        b = true;
    }
}

所以正确答案是B。

2.答案:
String s = (i < 40) ? "life" : (i > 50) ? "universe" : "everything";相当于:
String s = (i < 40) ? "life" : ((i > 50) ? "universe" : "everything");相当于:

String s;
if(i < 40){
    s = "life";
}else{
    if(i > 50){
        s = "universe";
    }else{
        s = "everything";
    }
}

所以正确答案是C。

3.答案:
注意10.9:9这里Java会根据运算符的精度自动进行类型转换。10.9的精度是double型,后面的9也自动转成double型了,
因此代码执行后结果为9.0。
所以答案是D。

4.答案:
&、|是位运算符,是操作二进制数的,所以要先把a、b转换为二进制数进行位运算后再转换为整型输出结果。
1的二进制是01,2的进制是10
a&b = 1 & 2 =
01
10
__
00 = 0;

a|b = 1 | 2 =
01
10
__
11 = 3;
所以输出结果为:
0
3

5.答案:
<<、>>是位移运算符,是操作二进制数的,所以要先把a、b转换为二进制数进行位移运算后再转换为整型输出结果。

public static void main(String[] args) {
    int a = 1;
    int b = 2;
    System.out.println(b << a);    //(b << a) = (0010 << 1) = 0100 = 4
    System.out.println(b >> a);    //(b >> a) = (0010 >> 1) = 0001 = 1
}

所以输出结果为:
4
1

6.答案:
注意当位移溢出时的计算结果。

public static void main(String[] args) {
    int a = 1;
    int b = 2;
    System.out.println(b << a << a);    //(b << a << a) = (b << 2) = (0010 << 2) = 1000 = 8  
    System.out.println(b >> a >> a);    //(b >> a >> a) = (b >> 2) = (0010 >> 2) = 0000 = 0
    System.out.println(b >> 32);    //(b >> 32) = (b >> (32%32)) = (b >> 0) = b = 2;    数据溢出时,位移数%数据最大范围,求余后重新计算
    System.out.println(b << 33);    //(b << 33) = (b << (33%32)) = (b << 1) = (0010 << 1) = 0100 = 4;    数据溢出时,位移数%数据最大范围,求余后重新计算
}

所以输出结果为:
8
0
2
4

                  算法          


1.输出数组里的所有值 答案:

//方法1 Arrays.toString(array)
public static void main(String[] args) {
    int[] array = new int[]{1, 2, 3, 4};
    System.out.println(Arrays.toString(array));    //[1, 2, 3, 4]
}
//方法2 for循环
public static void main(String[] args) {
    int[] array = new int[]{1, 2, 3, 4};
    int length = array.length;
    for (int i = 0; i < length; i++) {
        System.out.print(array[i] + " ");    //1 2 3 4
    }
}
//方法3 foreach循环
public static void main(String[] args) {
    int[] array = new int[]{1, 2, 3, 4};
    for(int v : array){
        System.out.print(v + " ");    //1 2 3 4
    }
}

2.输出99乘法口诀表 答案:

//方法1 用String
public static void NineNine(){
    String str = "";
    for (int i = 1; i <= 9; i++) {
        for (int j = 1; j <= i; j++) {
            str += j + "*" + i + "=" + j*i + "\t";
        }
        str += "\n";
    }
    System.out.println(str);
}

循环10W次时间:1180ms

//方法2 用StringBuilder
public static void NineNine(){
    StringBuilder sb = new StringBuilder();
    for (int i = 1; i <= 9; i++) {
        for (int j = 1; j <= i; j++) {
            sb.append(j);
            sb.append("*");
            sb.append(i);
            sb.append("=");
            sb.append(j*i);
            sb.append("\t");
        }
        sb.append("\n");
    }
    System.out.println(sb);
}

循环10W次时间:367ms

//方法3 一次循环完成
public static void NineNine(){
    int i = 1;  
    int j = 1;
    String str = "";
    while (i <= 9) {
        str += j + "*" + i + "=" + j*i + "\t";
        j++;
        if(j > i){
            i++;
            j = 1;
            str += "\n";
        }
    }
    System.out.println(str);
}

循环10W次时间:1197ms

//测试代码
public static void main(String[] args){
    long t1 = System.currentTimeMillis();
    for (int i = 0; i < 100000; i++) {
        //循环时注释掉System.out.println(str)
        NineNine();
    }
    long t2 = System.currentTimeMillis();
    System.out.println(t2 - t1);
}

3.输出字符串中出现次数最多的字符 答案:

//方法1
public static void printMaxChars(String str){
    HashMap<Character, Integer> map = new HashMap<Character, Integer>();
    int length = str.length();
    int max = 0;
    //循环字符串中的所有字符,记录每个字符出现的次数并获取最大次数
    for (int i = 0; i < length; i++) {
        int count = 0;
        char c = str.charAt(i);
        if(map.containsKey(c)){
            count = map.get(c);
        }
        count++;
        if(count > max){
            max = count;
        }
        map.put(c, count);
    }
    System.out.println("最大次数:" + max);
    //遍历map中的键,如果其值等于最大次数,则列出
    for (Character c : map.keySet()) {
        if(map.get(c).equals(max)){
            System.out.print(c + " ");
        }
    }
}

输出结果:
最大次数:4
c a
(输出结果还可以放进数组里排个序)

4.编写函数f(n), 获取0~n中“1”出现的次数 答案:

// 方法1:字符串判断
public static int get1Count(int num){
    int total = 0;
    String str;
    for (int i = 1; i <= num; i++) {
        str = String.valueOf(i);
        for (int j = 0; j < str.Length; j++) {
            if (str.charAt(i) == '1') total += 1;
        }
    }
    return total;
}

// 方法2:判断个位数是否为1
public static int get1Count(int num){
    int total = 0;
    for (int i = 1; i <= num; i++) {
        int n = i;
        if (n % 10 == 1) total += 1;
        while (n >= 10) {
            n = n / 10;
            if (n % 10 == 1) total += 1;
        }
    }
    return total;
}

方法2是方法1效率的数十倍

5.获取斐波那契数列的第n项值 答案:

// 方法1 递归
public static int Fibo(int n){
    return n < 3 ? 1 : Fibo(n - 2) + Fibo(n - 1);
}

计算n=1~40 时间:776ms

// 方法2 for循环
public static int Fibo(int n) {
    int a = 1;
    int b = 1;
    for (int i = 3; i <= n; i++) {
        int c = a + b;
        a = b;
        b = c;
    }
    return b;
}

计算n=1~500 循环1万次时间:462ms

// 方法3 for循环简化
// (理论上比方法2稍快 具体执行环境不同稍有差异 正负相差不大)
public static int Fibo(int n) {
    int a = 1;
    int b = 1;
    for (int i = 3; i <= n; i++) {
        b = a + b;
        a = b - a;
    }
    return b;
}

以上结果可以看出。虽然递归写法很简洁,但是效率太低,展开为for循环以后,效率极大提升。

// 测试代码
public static void FiboTest() {
    int times = 10000;
    int n = 500;
    long t0 = 0;
    long t1 = 0;
    /*
    // 输出斐波那契数列
    String msg = "";
    for (int i = 1; i <= 20; i++) {
        msg += Fibo(i) + " ";
    }
    System.out.println(msg);
    */
    
    /*
    // 递归
    t0 = System.currentTimeMillis();
    for (int j = 1; j <= 40; j++) {
        Fibo(j);
    }
    t1 = System.currentTimeMillis() - t0;
    System.out.println("递归:" + t1 + "ms");
    */
    
    //for循环
    t0 = System.currentTimeMillis();
    for (int i = 0; i < times; i++) {
        for (int j = 1; j <= n; j++) {
            Fibo(j);
        }
    }
    t1 = System.currentTimeMillis() - t0;
    System.out.println("for循环:" + t1 + "ms");
    
}
阅读 2.1k

冰封百度的学习笔记
程序生涯中的技术整理

Unity游戏程序员一枚。生命不息,学习不止。

196 声望
37 粉丝
0 条评论

Unity游戏程序员一枚。生命不息,学习不止。

196 声望
37 粉丝
文章目录
宣传栏