reoger的记录

--以后的你会感激现在那么努力的自己

0%

java知识点

面相对象的特征?

抽象、继承、封装、多态。
抽象:将一类对象的共同特征总结出来构造类的过程,包括数据抽象和行为抽象两方面。
继承:从已有类得到继承信息创建新类的过程,
封装:把数据和操作数据的方法绑定起来,对数据的访问只能通过已定义的接口。
多态:允许不同子类型的对象对同一消息做出不同响应,多态分为编译时多态和运行时多态。

String属于基本的数据结构吗?

不是。Java中的基本数据类型只有8个:byte、short、int、long、float、char、boolean;
除了基本类型和枚举类型,剩下的都是引用类型。

float f = 3.4;是否正确?

错误,3.4是双精度数,将双精度赋值给单精度属于向下转型,会造成精度损失。因此需要强制转换。

String和StringBuilder、StringBuffer的区别?

Java平台提供了两种类型的字符串:String和StringBuffer/StringBuilder,它们可以储存和操作字符串。其中String是只读字符串,也就意味着String引用的字符串内容是不能被改变的。而StringBuffer/StringBuilder类表示的字符串对象可以直接进行修改。StringBuilder是Java 5中引入的,它和StringBuffer的方法完全相同,区别在于它是在单线程环境下使用的,因为它的所有方面都没有被synchronized修饰,因此它的效率也比StringBuffer要高。

int和Integer有什么区别?

Integer是int的包装类,int是基本类型,integer是对象。使用intent值得注意的一点是,如果integer整型字面量的值在-128到127之间,那么不会new新的Integer对象,而是直接引用常量池中的Integer对象。例如题目:

1
2
3
4
5
6
7
8
   public static void main(String[] args) {
// TODO Auto-generated method stub
Integer f1 = 100, f2 = 100, f3 = 150, f4 = 150;
int f = 100;
System.out.println(f1 == f2);
System.out.println(f3 == f4);
System.out.println(f == f1);
}

输出的结果应该为 true,false,true;原因上面已经说过了。

内存中的栈(stack)、堆(heap)和静态区(static area),方法区的作用。

栈用于存放基本的数据类型、对象的引用和函数调用的现场保护等;
堆用于存放new关键字和构造器创建的对象;
静态区用于存放程序中的字面量,如直接书写100,”hello”和常量。
如语句: String str = new String(“hello”);
上面的语句中变量str放在栈上,用new创建出来的字符串对象放在堆上,而”hello”这个字面量放在静态区。
方法区:存放class二进制文件,包含类信息,静态变量,常量池,类的版本号等基本信息。方法区是各个线程共享的内存区域,用于存储class的二进制文件。

7. 构造器(construction)是否可以被重写(overrider)?

构造器不能被继承,因此不能被重写,但可以被重载。

8. 两个对象值相同( x.equals(y) == true ),那么他们的hashCode相同吗?

相同。在java中,hashCode值相同,他们并不一定相同(equals方法返回true),但是两个对象相同,他们的hasdCode一定相同。

9. 重载(Overload)和重写(Override)的区别。

方法的重载和重写都是实现多态的方式,区别在于前者实现的是编译时的多态性,而后者实现的是运行时的多态。重载发生在一个类中,同名的方法如果有不同的参数,则为重载;重写发生在子类和父类之间,重写要求子类被重写方法的与父类被重写的方法有相同的返回类型,方法名和参数;重载对返回类型则没有特殊的要求。

10. JVM加载class文件的原理机制?

JVM中类的装载是由类加载器(ClassLoader)和它的子类来实现的,Java中的类加载器是一个重要的Java运行时系统组件,它负责在运行时查找和装入类文件中的类。
由于Java的跨平台性,经过编译的Java源程序并不是一个可执行程序,而是一个或多个类文件。当Java程序需要使用某个类时,JVM会确保这个类已经被加载、连接(验证、准备和解析)和初始化。类的加载是指把类的.class文件中的数据读入到内存中,通常是创建一个字节数组读入.class文件,然后产生与所加载类对应的Class对象。加载完成后,Class对象还不完整,所以此时的类还不可用。当类被加载后就进入连接阶段,这一阶段包括验证、准备(为静态变量分配内存并设置默认的初始值)和解析(将符号引用替换为直接引用)三个步骤。最后JVM对类进行初始化,包括:1)如果类存在直接的父类并且这个类还没有被初始化,那么就先初始化父类;2)如果类中存在初始化语句,就依次执行这些初始化语句。
类的加载是由类加载器完成的,类加载器包括:根加载器(BootStrap)、扩展加载器(Extension)、系统加载器(System)和用户自定义类加载器(java.lang.ClassLoader的子类)。从Java 2(JDK 1.2)开始,类加载过程采取了父亲委托机制(PDM)。PDM更好的保证了Java平台的安全性,在该机制中,JVM自带的Bootstrap是根加载器,其他的加载器都有且仅有一个父类加载器。类的加载首先请求父类加载器加载,父类加载器无能为力时才由其子类加载器自行加载。JVM不会向Java程序提供对Bootstrap的引用。下面是关于几个类加载器的说明:

  • Bootstrap:一般用本地代码实现,负责加载JVM基础核心类库(rt.jar);
  • Extension:从java.ext.dirs系统属性所指定的目录中加载类库,它的父加载器是Bootstrap;
  • System:又叫应用类加载器,其父类是Extension。它是应用最广泛的类加载器。它从环境变量classpath或者系统属性java.class.path所指定的目录中记载类,是用户自定义加载器的默认父加载器。

11. char 型变量中能不能存贮一个中文汉字。

char类型可以存储一个中文汉字,因为Java中使用的编码是Unicode(不选择任何特定的编码,直接使用字符在字符集中的编号,这是统一的唯一方法),一个char类型占2个字节(16比特),所以放一个中文是没问题的。

12. 抽象类(abstract)和接口(interface)有什么异同?

抽象类和接口类都不能够实例化,但可以定义抽象类和接口类型的引用。一个类如果继承了某个抽象类或者实现了某个接口都需要对其中的抽象方法全部进行实现,否则该类仍然需要被声明为抽象类。
接口比抽象类更加抽象,因为抽象类中可以定义构造器,可以有抽象方法和具体方法,而接口中不能定义构造器而且其中的方法全部是抽象方法。
抽象类中的成员可以定义成员变量、而接口中定义的成员变量实际上都是常量。有抽象方法的类必须被声明为抽象类,而抽象类未必有抽象方法。
抽象类中的成员可以是private、protected、public的,而接口中的成员全部都是public。

13. 静态嵌套类(Static Nested Class)和内部类(Inner Class)的不同?

Static Nested Class是被声明为静态(static)的内部类,它可以不依赖于外部类实例被实例化。而通常的内部类需要在外部类实例化后才能实例化。要在静态方法中创建内部类对象,可以这样做:

1
new Outer().new Inner();

14. 静态变量和实例变量的区别。

静态变量是被static修饰符修饰的变量,也称为类变量,它属于类,不属于类的任何一个对象,一个类不管创建多少个对象,静态变量在内存中有且仅有一个拷贝;实例变量必须依存于某一实例,需要先创建对象然后通过对象才能访问到它。静态变量可以实现让多个对象共享内存。

15. 接口是否可继承接口?抽象类是否可实现接口?抽象类是否可继承具体类?

接口可以继承接口,而且支持多重继承。抽象类可以实现(implements)接口,抽象类可继承具体类也可以继承抽象类。

16. Throw和throws有什么区别?

throws是方法可能抛出异常的声明。用在方法方法函数头,表示抛出异常。throws表示出现异常的一种可能性,并不一定会发生这些异常;
throw是语句抛出一个异常。用在方法里,表示抛出了一个实实在在的异常,他必须要被处理。

17. final、finally、finalize的区别。

  • final:修饰符(关键字)有三种用法:如果一个类被声明为final,意味着它不能再派生出新的子类,即不能被继承,因此它和abstract是反义词。将变量声明为final,可以保证它们在使用中不被改变,被声明为final的变量必须在声明时给定初值,而在以后的引用中只能读取不可修改。被声明为final的方法也同样只能使用,不能在子类中被重写。
  • finally:通常放在try…catch…的后面构造总是执行代码块,这就意味着程序无论正常执行还是发生异常,这里的代码只要JVM不关闭都能执行,可以将释放外部资源的代码写在finally块中。
  • finalize:Object类中定义的方法,Java中允许使用finalize()方法在垃圾收集器将对象从内存中清除出去之前做必要的清理工作。这个方法是由垃圾收集器在销毁对象时调用的,通过重写finalize()方法可以整理系统资源或者执行其他清理工作。

18. Collection和Collections的区别?

Collection是一个接口,它是Set、List等容器的父接口;Collections是个一个工具类,提供了一系列的静态方法来辅助容器操作,这些方法包括对容器的搜索、排序、线程安全化等等。

19. List、Set、Map是否继承自Collection接口?

List、Set 是,Map 不是。Map是键值对映射容器,与List和Set有明显的区别,而Set存储的零散的元素且不允许有重复元素(数学中的集合也是如此),List是线性结构的容器,适用于按数值索引访问元素的情形。

20. Sleep()方法和wait()方法有什么异同?

相同:都可以让线程处理冻结状态。
不同点:sleep()是Thread类中定义的方法,wait()是Object类中定义的方法;
Sleep()必须指定时间,而wait()可以指定也可不指定;
Sleep()不会释放锁,而wait()释放锁;
Sleep()需要捕获异常,而wait()只能在(synchronized)环境中使用。
Sleep()睡眠后不出让系统资源,wait让出系统资源其他线程可以占用CPU

21. 抽象的(abstract)方法是否可以同时是静态的(static),是否可同时是本地方法(native),是否可同时被synchronized修饰?

都不能。抽象方法需要子类重写,而静态的方法是无法重写的,因此二者是矛盾的。本地方法是由本地代码(如c/c++)实现的方法,而抽象方法是没有实现的,也是矛盾的。Synchronied和方法的实现细节有关,抽象方法不涉及实现细节,因此也是相互矛盾的。

22. Error和Exception有什么区别?

Error表示系统级的错误和程序不必处理的异常,是恢复不是不可能但很困难的情况下的一种严重问题;比如内存溢出,不可能指望程序能处理这样的情况;
Exception表示需要捕捉或者需要程序进行处理的异常,是一种设计或实现问题。也就是说,他表示如果程序运行正常,从不会发生的情况。

23. 多线程编程有几种实现方式?

Java 5以前实现多线程有两种实现方法:一种是继承Thread类;另一种是实现Runable接口。两种方式都要重写run()方法来定义线程的行为,推荐使用后者,因为java中的继承是单继承,显然接口更加灵活。

24. Thread类中的start()和run()方法有什么区别?

Start()方法被用来启动新创建的线程,而且start()内部调用了run()方法,这和直接调用run()方法的效果不一样。当你调用run()方法的时候,只会是在原来的线程中调用,没有在新的线程中调用,没有新的线程启动,start()方法才会启动新的线程。

25. Java中的volatile 变量是什么?

volatile是一个特殊的修饰符,只有成员变量才能使用它。在Java并发程序缺少同步类的情况下,多线程对成员变量的操作对其它线程是透明的。volatile变量可以保证下一个读取操作会在前一个写操作之后发生。

26. 什么是ThreadLocal变量?

ThreadLocal是Java里一种特殊的变量。每个线程都有一个ThreadLocal就是每个线程都拥有了自己独立的一个变量,竞争条件被彻底消除了。它是为创建代价高昂的对象获取线程安全的好方法,比如你可以用ThreadLocal让SimpleDateFormat变成线程安全的,因为那个类创建代价高昂且每次调用都需要创建不同的实例所以不值得在局部范围使用它,如果为每个线程提供一个自己独有的变量拷贝,将大大提高效率。首先,通过复用减少了代价高昂的对象的创建个数。其次,你在没有使用高代价的同步或者不变性的情况下获得了线程安全。线程局部变量的另一个不错的例子是ThreadLocalRandom类,它在多线程环境中减少了创建代价高昂的Random对象的个数。 当然,可以参考《android艺术探索》P375 了解ThreadLocal原理。

27. 有三个线程,怎么确保他们顺序执行?

在多线程中有多种方法让线程按特定顺序执行,你可以用线程类的join()方法在一个线程中启动另一个线程,另外一个线程完成线程继续执行;
你也可以用java中的锁机制(ReentrantLock、或者newCondition),在一个线程执行的时候,让他占有锁,线程执行完毕才释放锁;
也可以利用三个信号量来让三个线程按顺序执行,刚开始的时候设置只有第一个线程可以获取信号量,第一个线程运行完毕后释放第二个信号量,以此启动第二个线程。
甚至你可以将这三个线程放入线程池,利用线程池来让他们按顺序执行。
如果上面的讲述不是很清楚,可以参考代码

28. Java中如何停止一个线程?

JDK 1.0本来有一些像stop(), suspend() 和 resume()的控制方法但是由于潜在的死锁威胁因此在后续的JDK版本中他们被弃用了,之后Java API的设计者就没有提供一个兼容且线程安全的方法来停止一个线程。当run() 或者 call() 方法执行完的时候线程会自动结束。如果要手动结束一个线程,你可以用volatile 布尔变量来退出run()方法的循环或者是取消任务来中断线程;也可以使用inerrupt方法终止线程,但interrupt并不一定会终止线程,该方法只是设置了一个中断状态。当然,停止线程也可以通过return语句来实现,不过个人推荐使用异常来停止线程,因为抛出的异常可以传递线程停止的信息而通过return语句就不能传递。

29. Switch能否用string做参数?

不能。在java 7以前,switch只能支持byte、short、char、int或者对应的封装类以及enum类型。在java 7中,switch支持string了,但是不支持long。

30. Java中四种引用的区别?

强引用:如果一个对象具有强引用,它就不会被垃圾回收器回收。即使当前内存空间不足,JVM也不会回收它,而是抛出 OutOfMemoryError 错误,使程序异常终止。如果想中断强引用和某个对象之间的关联,可以显式地将引用赋值为null,这样一来的话,JVM在合适的时间就会回收该对象
软引用:在使用软引用时,如果内存的空间足够,软引用就能继续被使用,而不会被垃圾回收器回收,只有在内存不足时,软引用才会被垃圾回收器回收。
弱引用:具有弱引用的对象拥有的生命周期更短暂。因为当 JVM 进行垃圾回收,一旦发现弱引用对象,无论当前内存空间是否充足,都会将弱引用回收。不过由于垃圾回收器是一个优先级较低的线程,所以并不一定能迅速发现弱引用对象
虚引用:顾名思义,就是形同虚设,如果一个对象仅持有虚引用,那么它相当于没有引用,在任何时候都可能被垃圾回收器回收。

31. hashMap和hashTable的区别?

hashMap是非synchronied的(即线程安全的),而hashTable是线程安全的(使用synchronied修饰,代价就是效率变低)。
hashMap 可以接受null(即可以将键值或者值设置为null),但是hashTable不行。
hashMap中hash数组默认大小是11,增加的方式是old*2+1,hashMap中hash数组的默认大小是16,而且一定是2的指数。
hasMap是Map接口的一个实现,而Hashtable是基于陈旧的Dictionary类,完成了Map接口;

32. ArrayList和LinkedList的区别。

ArrayList的实现为动态数组,初识大小为10,大小不够会自动调用grow扩容:length = length+(length>>1);
LinkedList的实现为双向链表,没有默认的大小。

33. &和&&的区别

  • &表示位运算与,不会短路;
  • &&表示逻辑运算与,在第一个条件为false的情况下会短路。

34. 在java中如何跳出当前多重循环?

我们可以在外层循环添加一个标号(以”:”结束),当我们需要结束循环时,我们可以直接break +外层循环的标号;
当然,我们可以在外层循环中添加一个bool值的变量,当门需要退出时,改变bool的值让外层循环停止即可。

35. Synchronized锁对象与锁方法、代码块区别。

当synchronized锁的是对象,两个线程分别访问同一个类的同一个实例的相同方法时,他们会按照会同步执行两个类中所有被调用的方法;而当synchronized锁的是方法时,他们只会同步执行这个被锁住的方法,而当synchronized是一个代码块的时候,就意味着只有这个方法块才会同步执行。

36. 字节流和字符流的区别?

字节流用于读取或写出二进制数据,比如图片、影像等数据,几乎所有的数据都可以通过字节流来处理;字节流的基本单元为字节;字节流默认不使用缓存区;
字符流用于读取或写出字符数据,比如传输字符串;字符流的基本单元为Unicode码元;字符流默认使用缓存区;

37. TreeMap,LinkedHashMap,HashMap的区别是什么?

hashMap底层实现是散列表,因此它内存存储的元素的无序的;
TreeMap的底层实现是红黑树,所以它内部的元素是有序的。排序的依据是自然序或者是创建TreeMap时所提供的比较器(Comparator)对象;
LinkedHashMap能够记住插入元素的顺序。

38. 说说设计模式

详细资料可以参考这里
简单工厂模式:它属于类创建型模式。在简单工厂模式中,可以根据参数的不同返回不同类型的实例。简单工厂模式专门定义一个类来负责创建其他类的实例。
https://github.com/mingjunli/JavaDesignPatterns

39. int-char-long在java中各占多少字节?

Byte Short Int Long Float Double Char
位数 8 16 32 64 32 64
字节数 1 2 4 8 4 8