一、不定项选择
1
String s = new String("xyz");
创建了几个StringObject? B
A:两个或者一个都有可能
B:两个
C:一个
D:三个
String a= "xyz";在字符串常量池中直接开辟xyz ,所以是一个StringObject.
String b=new String("xyz"),首先在堆内存开辟内存空间,栈内存中的变量 b 指向它,而它真正的值指向 放在字符串常量池当中的开辟的xyz,所以两个 StringObject
字符串常量池特点:数据共享,如果没写String a="xyz",那String b=new String("xyz"),开辟两个StringObject;如果写了String a="xyz",那就开辟只堆内存中的StringObject,String a="xyz"在字符串常量池已开辟了xyz 不需要他在开辟,直接指向。如图
2.下列关于final,finally和finalize的说法正确的是()ABD
A:final可以用来修饰类(不能被继承)、方法(不能被重写)、变量(表示常量)
B:finally是java代码保证重点代码一定要执行的一种机制
C:变量被final修饰后不能再指向其他对象,
但可以重写//不可以重写D:finalize设计目的是保证对象在被垃圾收集完成特定资源回收
3.局部内部类可以用那些修饰符修饰?CD
A:public
B:private
C:abstract
D:final
4.执行下列代码会发生什么?D
public class Test {
static {
int x = 5; //提前表达 撤出内存
}
static int x,y;
public static void main(String[] args) {
x--; //-1
myMethod();
System.out.println(x+y+ ++x);//1+0+2 }
public static void myMethod() {
y = x++ + ++x;// -1+1
}
}
A:编译出错
B:输出1
C:输出2
D:输出3
E:输出7
F:输出8
java文件(十进制文件)通过javac 命令 编译成.class文件(二进制字节码文件)本质在磁盘中,通过java 命令再加载到内存中,加载进方法区,其中static修饰的会提前进行表达在main方法之前。static代码块 中 x=5 入栈完 马上出栈,没有任何意义。之后正常计算即可
5.以下程序的输出结果 JAVA执行顺序 D
class Base {
public Base(String s) {
System.out.println("B");
}
}
public class Dervid extends Base {
public Dervid(String s) {
System.out.println("D");
}
public static void main(String[] args) {
System.out.println("C");
}
}
A:BD
B:DB
C:C
D:编译错误
子类要有super(),指向父类
子类给父类提供参数,super指向父类,(this指向当前对象)
6.java继承的特点,下列说法正确的是 B
A
:使类的定义复杂化B:java只支持单继承,不可多继承,但可以通过实现接口来达到多继承的目的
C:子类继承父类的
所有成员变量和方法,包括父类的构造方法 //私有不能继承D:不可以多层继承,既一个类不可以继承一个类的子类
继承的本质:代码的复用
7.关于final关键字下列说法正确的是 C
A:如果修饰局部变量必须初始化 //初始化就是赋值 不用必须先赋值
B:如果修饰类,则该类只能被一个子类继承//修饰类 不能被继承
C:如果修饰方法,则该方法不能在子类当中重写
D:如果修饰方法,则该方法所在的类不能被继承//finall 修饰方法不能被子类重写
8.下列说法正确的是 B
A:在类方法当中可以用this来调用本类的方法 //static 修饰方法
B:在类方法当中调用本类的类方法可以直接调用
C:在类方法当中
只调用本类的方法D:在类方法中绝对不能调用实例方法 (new 对象) //实例 没有 static 修饰的方法
9.下列说法正确的是() B
A:在类当中定义的变量称为类的成员变量,
在别的类当中可以直接使用B:局部变量的作用范围仅仅在定义它的方法内,或者在定义它的控制流块中
C:使用别的类的方法
只需要引用方法名即可D:只要没有定义不带参数的构造函数,JVM都会为类生成一个默认的构造函数//写了构造函数,默认就会消失
10.java 反射机制主要提供了以下哪些功能? ABCD
A:在运行时判断一个对象所属的类
B:在运行时构造一个类的对象
C:在运行时判断一个类所具有的成员变量和方法
D:在运行时调用一个对象的方法
11.在java 当中下列说法错误的是 BCD
A:数组是一种对象
B:数组属于原生类 //java没有原生类概念
C:int num = []{1,2,3,4} //格式错误
D:
数组的大小可以任意改变
12.关于java的一些概念那些是正确的?B
A:所有的java
异常错误都是java.lang.Exception 包括java.lang.RuntimeException// 异常和错误是两个概念B:通过try catch finally语句finally无论发生什么异常都会得到执行
C:Java中所有数据都是对象
D:Java语言是跨平台的,无论通过那个版本编写的java程序,都能在所在的java平台当中运行
13.下列程序的运行结果 B
class Two{
Byte x; //大写Byte 默认null
}
public class Student {
public static void main(String[] args) {
Student student = new Student();
student.start();
}
void start() {
Two two = new Two();
System.out.print(two.x +" ");
Two two2 = fix(two);
System.out.println(two.x + " "+two2.x);
}
Two fix(Two tt) {
tt.x = 42;
return tt;
}
}
A: null null 42
B:null 42 42
C:0 0 42
D:0 42 42
E:Anexception is thrown at runtime
第一步 main方法入栈,创建student对象,指向堆内存种实际的student对象,其中有两个方法 start(); fix();。然后调用start(),new一个对象 two ,指向的堆内存种实际的Two对象,其中有Byte 类型的 x,此处注意 是Byte B是大写的 所以 x 的默认值是null,然后第一句输出自然是null。,之后调用fix方法,入栈之后,有参数叫 tt ,要把 two 传进去,实际传的是two 的地址值(假设叫 0x2),之后 tt.x=42,return tt。 return出去后被变量 two2 接收 0x2这个参数,之后输出 two.x 和 two2.x 都指向 x=42。
二、简答题(每题5分)
1.java的跨平台优势?
不同的操作系统上有不同的虚拟机,JVM屏蔽了底层运行平台的差别,实现了“一次编译,到处运行”。在某个操作系统平台上,开发,编译出来的字节码文件,可以在其他的操作系统平台上运行。
在不同的操作系统平台上,安装了对应操作系统的不同版本的jvm虚拟机(java的运行容器)。不同版本的虚拟机,在不同的操作系统平台上,营造出来的运行环境是一样的,所以具备了跨平台性
2.简述java中==和equals的区别
- ==是运算符,用于比较两个变量是否相等,对于基本类型而言比较的是变量的值,对于对象类型而言比较的是对象的地址.
- equals() 是Object类的方法,用于比较两个对象内容是否相等.默认Object类的 equals() 实现如下:
public class Object {
......
public boolean equals(Object obj) {
return (this == obj);
}
......
}
不难看出此时equals()是比较两个对象的地址,此时直接==比较的的结果一样.对于可能用于集合存储中的对象元素而言,通常需要重写其equals()方法.
3.重载和重写的区别是什么?
重载(Overload)是让类以统一的方式处理不同类型数据的一种手段,实质表现就是多个具有不同的参数个数或者类型的同名函数(返回值类型可随意,不能以返回类型作为重载函数的区分标准)同时存在于同一个类中,是一个类中多态性的一种表现(调用方法时通过传递不同参数个数和参数类型来决定具体使用哪个方法的多态性)。
重写(Override)是父类与子类之间的多态性,实质是对父类的函数进行重新定义,如果在子类中定义某方法与其父类有相同的名称和参数则该方法被重写,不过子类函数的访问修饰权限不能小于父类的;若子类中的方法与父类中的某一方法具有相同的方法名、返回类型和参数表,则新方法将覆盖原有的方法,如需父类中原有的方法则可使用 super 关键字。
4.重写equals方法为什么一定要重写hashcode()方法
重写 equals 一定要重写 hashcode
因为 hashmap中 equals 与hashcode 协同,用equals 判断对象值是否相等,根据hashcode 存储
5.接口和抽象类的区别?
接口是行为的抽象,是一种行为的规范,接口实现的目的主要是多继承;
抽象类是对类功能的提取,是一种模板设计
6.请简述java异常体系
java异常体系
Thorwable类(表示可抛出)是所有异常和错误的超类,两个直接子类为Error和Exception,分别表示错误和异常。
其中异常类Exception又分为运行时异常(RuntimeException)和非运行时异常, 这两种异常有很大的区别,也称之为不检查异常(Unchecked Exception)和检查异常(Checked Exception)。
Error与Exception
Error是程序无法处理的错误,它是由JVM产生和抛出的,比如OutOfMemoryError、ThreadDeath等。这些异常发生时,Java虚拟机(JVM)一般会选择线程终止。
Exception是程序本身可以处理的异常,这种异常分两大类运行时异常和非运行时异常。程序中应当尽可能去处理这些异常。
运行时异常和非运行时异常
运行时异常都是RuntimeException类及其子类异常,如NullPointerException、IndexOutOfBoundsException等,这些异常是不检查异常,程序中可以选择捕获处理,也可以不处理。这些异常一般是由程序逻辑错误引起的,程序应该从逻辑角度尽可能避免这类异常的发生。
非运行时异常是RuntimeException以外的异常,类型上都属于Exception类及其子类。从程序语法角度讲是必须进行处理的异常,如果不处理,程序就不能编译通过。如IOException、SQLException等以及用户自定义的Exception异常,一般情况下不自定义检查异常。
7.访问修饰符public、private、protected、以及不写(default默认)时的区别?
8.请简述java 128陷阱
public static void main(String[] args) {
Integer num1 = 100;
Integer num2 = 100;
System.out.println(num1 == num2);
Integer num3 = 128;
Integer num4 = 128;
System.out.println(num3 == num4);
}
答案就在Integet的valueOf()方当中,如果我们的数值在-128-127之间的数值都存储在有一个catch数组当中,该数组相当于一个缓存,当我们在-128-127之间进行自动装箱的时候,我们就直接返回该值在内存当中的地址,所以在-128-127之间的数值用==进行比较是相等的。而不在这个区间的数,需要新开辟一个内存空间,所以不相等。
9.如何忽略安全访问修饰符的安全检查
忽略安全访问修饰符的安全检查 setAccessible(true) //暴力反射 ---》private
10.获取通过反射Class对象的三种方式
1.Object类中的getClass方法,getClass()方法在object类当中定义着
2.通过对象静态属性 .class来获取对应的Class对象
3.1.Class.forName("全类名"):将字节码文件加载进内存,返回class对象.
只要通过给定类的字符串名称就可以获取该类,更为拓展
11.请简述static关键字
12.请简述final关键字
13.请简述this关键字
14.请简述构造器的特点
1.构造器要与类同名
2.当我们new对象时,new 后边的方法就代表着我们的构造函数
3.我们的每一个类当中都有一个默认的不显示的无参构造器,当我们在这个类当中重写写一个构造器的时候,我们默认调用的就是我们显示的构造器
4.我们的构造器是没有返回值的,如果有返回值,即便你的方法名和类名相同那么也不是构造函数 5.我们的类当中是有一个或一个以上的构造函数
15.简述每一个输出的原因 多态
public class A {
public String Show(D obj) {
return "A and D";
}
public String Show(A obj) {
return "A and A";
}
}
public class B extends A{
public String Show(Object obj) {
return "B and B";
}
public String Show(A obj) {
return "B and A";
}
}
public class C extends B{
}
public class D extends B{
}
测试类:
public class Test {
public static void main(String[] args) {
A a1 = new A();
A a2 = new B();
B b = new B();
C c = new C();
D d = new D();
System.out.println("1---"+a1.Show(b));//B向上转型,父类的引用指向子类对象
System.out.println("2---"+a1.Show(c));//C向上转型
System.out.println("3---"+a1.Show(d));//直接接收
System.out.println("4----"+a2.Show(b));
System.out.println("5----"+a2.Show(c));
System.out.println("6----"+a2.Show(d));
System.out.println("7---"+b.Show(b));
System.out.println("8---"+b.Show(c));
System.out.println("9---"+b.Show(d));
}
}
首先定义类 A 有两个show 方法 ,java中方法名相同,那参数必须得不同,类B 也是这样。
本题继承链
前三个:首先 main方法入栈 创建a1,因为 new A();,,第一个 调用show方法,传B 类型对象b ,
调用show(A obj),这是多态中的向上转型(父类引用指向子类对象),所以输出 A and A
第二个 c 是 new c(); 但是两个show方法中没有所指定的类型,所以 向上转型,转型到 B,然后 B再向上转型到 A,所以输出 A and A
第三个 传的是 D类型的对象b,直接调用show(D obj),所以输出 A and D
中间 三个 4 ,5,6 难
main 创建 a2,A类型的对象,但是是new B,创建子类对象的同时一定会创建父类对象,只有这样子类才能覆盖父类的方法,父 子类对象中有相同的方法,方法的重写:子类重写父类方法,showA方法来自B当中。,继承的本质就是代码的复用。子类既可以用父类的又可以用自己的,但是现在是多态,只能调用本身的,A类型的对象只能调用 show D 和show A(这个show A 来自B当中),类型决定指向什么样的数据。所以A B
同时创建出来了,A类型只能指向A当中的,如果是B 那都能指向。
第四个 输入 b 向上转型 输出 B and A
第五个 同理 输出 B and A
第六个 直接接收, 输出 A and D
------- 7 8 9
定义 B 类型数据,new B(),能把父类A全部全部创建出来,图同上,,
第七个,传 b 向上转型,到 A,输出 B and A
第八个 同理 输出 B and A
第九个 直接调用 A and D
16.以下的输出是什么?为什么?
public static void main(String[] args) {
int a = 10;
int b = 10;
Integer a1 = 10; //
Integer b1 = 10;
Integer a2 = new Integer(10);
Integer b2 = new Integer(10);
System.out.println(a == b); // T 基本数据类型 == 比较值
System.out.println(a1 == b1); // T 128陷阱 引用类型比较地址
System.out.println(a2 == b2); // F 引用数据类型 == 比较地址 new重新开辟空间
System.out.println(a1 == a); // T 用 == 判断,自动拆箱 integer--》int
System.out.println(a1.equals(a)); T // 用 equals() 判断,自动装箱 int--》integer ,这个地方要给同学们讲一下Integer类当中的equals()
System.out.println(a1 == a2);//F 比较地址
System.out.println(a == a2);//T 自动拆箱
}