以下内容大部分来自网络,自己做了小部分修改
- final,finally,finalize的区别
final是java的关键字,被其修饰的类不能被继承,故一个类不能同时被abstract和final修饰;被修饰的final修饰的方法只能被使用,而不能被覆写、重载;被fanla修饰的变量只能被引用,而不能修改,故要有初始值。
finally通常与catch一起使用,保证无论程序抛出exception与否都要执行finally代码块,即使在catch中return退出了函数。
finalize是一个方法名,这个方法由垃圾收集器确定对象未被使用时调用,将对象销毁。
- anonymousinnerclass(匿名内部类)是否可以extends(继承)其它类,是否可以implements(实现)interface(接口)?
new <类或接口> <类的主体>
可以继承和实现接口,但都尽限一个,为什么?先请看代码
interface IA{
public void print();
}
abstract class B{
public abstract void print();
}
class D{
public static void test() {
new IA() {
public void f(){System.out.println("BBB");}
@Override
public void print() {
// TODO Auto-generated method stub
}
};
new B() {
@Override
public void print() {
// TODO Auto-generated method stub
}
};
}
}
匿名内部类的继承或实现接口时,声明时,类名要和抽象类或接口名一致。
- static nested class和inner class的不同
static nested class 指静态嵌套类,或称嵌套类,是C++中常用的说法,inner class指内部类,是JAVA中的说法.
内部类是一个类内部的类的统称,具体分为四种:成员类,静态成员类,局部类,匿名类.
其中匿名类是局部类的特殊情况.
//匿名类上个问题有,不说了
class D{
public static void test() {
class A{
void print() {
System.out.println();
}
};
}
}
对于成员类和静态成员类都存在于类的顶层代码中,相当于类的静态方法和非静态方法的关系。区别在于 成员类依赖于类实例而静态成员类不依赖.所以前者只能访问实例方法和成员而后者只能访问静态方法和成员。
class A{
public class C{};
static class D{};
}
public class Main {
public static void main(String[] args) {
// TODO Auto-generated method stub
System.out.println("匿名内部类");
A.D d = new A.D();
A a = new A();
A.C c = a.new C();
}
}
- &和&&的区别。
位运算符和逻辑运算符 - hashmap和hashtable的区别
- collection和collections的区别
什么时候用assert
使用assert需要开启-ea开关,执行程序
1、assert关键字需要在运行时候显式开启才能生效,否则你的断言就没有任何意义。而现在主流的Java IDE工具默认都没有开启-ea断言检查功能。这就意味着你如果使用IDE工具编码,调试运行时候会有一定的麻烦。并且,对于Java Web应用,程序代码都是部署在容器里面,你没法直接去控制程序的运行,如果一定要开启-ea的开关,则需要更改Web容器的运行配置参数。这对程序的移植和部署都带来很大的不便。
2、用assert代替if是陷阱之二。assert的判断和if语句差不多,但两者的作用有着本质的区别:assert关键字本意上是为测试调试程序时使用的,但如果不小心用assert来控制了程序的业务流程,那在测试调试结束后去掉assert关键字就意味着修改了程序的正常的逻辑。
3、assert断言失败将面临程序的退出。这在一个生产环境下的应用是绝不能容忍的。一般都是通过异常处理来解决程序中潜在的错误。但是使用断言就很危险,一旦失败系统就挂了。
所以测试的时候时候断言就可。gc是什么?为什么要有gc?
GC 即 garbage collection(垃圾收集),是JAVA用于回收内存的一种方式,主要的实现方法有引用计数,标记回收,复制清除等,GC可以避免内存泄露和堆栈溢出,有效提高内存的利用效率,同时将程序员从繁琐的内存管理中释放出来.
System类里有个gc()函数,供程序员调用回收内存。那为什么有了垃圾回收机制了,还要使用gc()呢,请看下面代码
a.v = b;
b.v = c;
/*
*Watch out !
*b仍然有指向!!
*/
a.v = d;
- string s=new string(“xyz”);创建了几个stringobject?
2个,文字池中1个,堆中1个.先在文字池中创建1个”xyz”对象,再在堆中拷贝一个”xyz”对象,并将其赋给引用s. - Math.round(11.5)和Math.round(-11.5)
结果为12和-11.因为四舍五入。 - short s1=1;s1=s1+1;有什么错?short s1=1;s1+=1;有什么错?
s1=s1+1会出错,s1+1是int型,不能将int赋值给s1.需要显示转换,s1=(int)(s1+1).而s1+=1不会出错,至于原因,有人说和编译器的机制有关,需要看编译原理。 - sleep()和wait()有什么区别?
1,sleep()是java.lang.Thread中的静态方法,wait()是java.lang.Object中的方法
2,sleep()用作当前线程阻塞自己,并在制定时间后恢复,wait()用于当前线程决定其他线程阻塞,是线程通信的表现.
3,sleep()不释放资源,wait()释放资源.
4,sleep()必须捕获异常,而wait()不需要. - java有没有goto?
有,但不用常用,可读性不高 - 数组有没有length()这个方法?string有没有length()这个方法?
数组没有,lenght有 - overload和override的区别。overloaded的方法是否可以改变返回值的类型?
Overload是重载的意思,Override是覆盖的意思,也就是重写。
重载Overload,类内定义。表示同一个类中可以有多个名称相同的方法,但这些方法的参数列表各不相同(即参数个数或类型不同)。重载不能根据放回值来区分。
重写Override,因子类和父类的关系定义。表示子类中的方法可以与父类中的某个方法的名称和参数完全相同,通过子类创建的实例对象调用这个方法时,将调用子类中的定义方法,这相当于把父类中定义的那个完全相同的方法给覆盖了,这也是面向对象编程的多态性的一种表现。
那overloaded的方法是否可以改变返回值的类型?
不可以。因为若这样改了,它就不能实现多态。
错误提示
class A{
public void print() {
System.out.println("A");
};
}
class B extends A{
//错误提示: The return type is incompatible with A.print()
public int print() {
return 1;
};
}
class C extends A{
//错误提示: The return type is incompatible with A.print()
public String print() {
return "hello";
};
}
/*
*若一个方法传入的是<?extends A>请如何调用print方法
*/
- set里的元素是不能重复的,那么用什么方法来区分重复与否呢?是用hashcode()还是equals()?它们有何区别?
这个属于集合类的查找机制问题,在集合类中,确定两个元素是 否相同,是用equals方法进行比较,hashcode的存在在于可以给元素快速分配一个index来存储.可以将collection看做很多个大箱 子,index是箱子的编号,先将要扔进去的物品进行hash确定index,扔进响应箱子,然后再和箱子里的其它物品equals()来比较是否相同.
此外,相等的物品一定具有相同的hashcode,不等的物品不一定.具有相同hashcode的元素不一定相等.不同的hashcode的元素肯定不 等.以上规则可以想象一下相等物品一定要分在同一个箱子中的情况.
class Person{
int age;
String name;
@Override
public int hashCode() {
return 1;
}
public Person(int age, String name) {
super();
this.age = age;
this.name = name;
}
@Override
public boolean equals(Object obj) {
if (this == obj)
return true;
if (obj == null)
return false;
if (getClass() != obj.getClass())
return false;
Person other = (Person) obj;
if (age != other.age)
return false;
if (name == null) {
if (other.name != null)
return false;
} else if (!name.equals(other.name))
return false;
return true;
}
@Override
public String toString() {
return "Person [age=" + age + ", name=" + name + "]";
}
}
public class Main {
public static void main(String[] args) {
Set<Person> set = new HashSet<Person>();
set.add(new Person(10,"张三"));
set.add(new Person(10,"张三"));
set.add(new Person(10,"张三"));
Iterator<Person> it = set.iterator();
while(it.hasNext()) {
System.out.println(it.next());
}
}
}
给我一个你最常见到的runtimeexception
可以查java的api文档的java.lang包
NullPointerException - 空指针引用异常
ClassCastException - 类型强制转换异常。
IllegalArgumentException - 传递非法参数异常。
ArithmeticException - 算术运算异常
ArrayStoreException - 向数组中存放与声明类型不兼容对象异常
IndexOutOfBoundsException - 下标越界异常
NegativeArraySizeException - 创建一个大小为负数的数组错误异常
NumberFormatException - 数字格式异常
SecurityException - 安全异常
UnsupportedOperationException - 不支持的操作异常list,set,map是否继承自collection接口?
list和set是,colletion不是,这查api文档或源代码都知道- abstractclass和interface有什么区别
抽象类可以有抽象方法和普通方法,也可以有自己的数据成员.接口只允许有常量,抽象方法和静态类成员.
接口可以被多实现,抽象类不多继承.接口被实现时,所有方法必须被重写.抽象类被继承时如果有抽象方法没被重写,则子类也为抽象类.
不过JDK1.8有了新的改变,interface可以有default和static完整方法
interface A{
public static void print() {
System.out.println("我是A的静态方法");
}
public default void defaultPrint() {
System.out.println("我是A的default方法");
}
}
- abstract的method是否可同时是static,是否可同时是native,是否可同时是synchronized?
abstact方法需要子类重写,重写的概念是就实例方法而 言, 所以不能是static.因为同一原因,要重写就不能native。
synchronized是同步,没实现也同步不起来。
abstract class D{
//Eclipse竟然显示的错误是The abstract method print in type D
//can only set a visibility modifier, one of public or //protected
abstract synchronized void print();
}
abstract方法的修饰符只有protected和public.因为你私有了,怎么override。
- 启动一个线程是用run()还是start()?
- 构造器constructor是否可被override?
构造器(override)不能被继承,因此不能重写overriding - 是否可以继承string类
String类为final,不可被继承. 当一个线程进入一个对象的一个synchronized方法后,其它线程是否可进入此对象的其它方法?
对象的synchronized方法不能进入了,但它的其他非synchronized方法还是可以访问的。
class C {
public synchronized void print(String msg) {
System.out.print(“print方法”+msg+”\n”);
try {
Thread.sleep(5000);
} catch (InterruptedException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
public synchronized void println(String msg) {
System.out.println(“println方法”+msg+”\n”);
}
}
public class Main {
public static void main(String[] args) {
C c = new C();new Thread(()-> { c.print(Thread.currentThread()+"我占用啦,哈哈哈!!"); }).start();; new Thread(()-> { c.println(Thread.currentThread()+"我占用啦,哈哈哈!!"); }).start();;
}
}- synchronized和lock的区别
- try{}里有一个return语句,那么紧跟在这个try后的finally{}里的code会不会被执行,什么时候被执行,在return前还是后?
class C {
public String ret() {
try {
return "我是try";
}catch(Exception e) {
e.printStackTrace();
}finally {
return "我是finally";
}
}
}
public class Main {
public static void main(String[] args) {
C c = new C();
System.out.println(c.ret());
}
}
输出:
"我是finally"
我发现额外的错误
class C {
编译错误提示:Unreachable codeThis method must return a result of type String
public String ret() {
try {
return "我是try";
}catch(Exception e) {
e.printStackTrace();
}finally {
//return "我是finally";
}
}
}
class C {
public String ret() {
try {
return "我是try";
}catch(Exception e) {
e.printStackTrace();
}finally {
return "我是finally";
}
//编译错误提示:Unreachable code
return "我是end";
}
}
我终于知道finally必须执行的原因了,它的地位比任何return还高。
- 用最有效率的方法算出2乘以8等於几
用位移
int x=2;
x=x<<2; //乘两次2
x=x>>4; //除四次2
两个对象值相同(x.equals(y)true),但却可有不同的hashcode,这句话对不对?
当一个对象被当作参数传递到一个方法后,此方法可改变这个对象的属性,并可返回变化后的结果,那么这里到底是值传递还是引用传递?
引用传递,毫无疑问,对象传递只能是引用.你可以换改变引用的内容,但并不能改变引用本身.- swtich是否能作用在byte上,是否能作用在long上,是否能作用在string上?
错误提示: Cannot switch on a value of type long. Only convertible int values, strings or enum variables are permitted
switch可作用于char 、byte 、short、 int
switch可作用于char、 byte 、short 、int对应的包装类
switch不可作用于long、 double、 float、 boolean,包括他们的包装类
swith还可以作用于String、enum变量
// 错误提示: Cannot switch on a value of type long. Only convertible int values,
// strings or enum variables are permitted
long d=3;
switch(d){}
- 编程题:写一个singleton出来