常见问题之java基础

111 阅读5分钟

「这是我参与2022首次更文挑战的第5天,活动详情查看:2022首次更文挑战」。

java有几种数据类型

基本类型:

1.数值:byte,short ,int,long  
2.小数类型:float,double  
3.布尔类型:boolean  

引用类型:

类,接口,数值

访问修饰符有哪些

1.private  当前类   
2.default  当前类,当前包   
3.protected 当前类,当前包,子类   
4.public 当前类,当前包,子类,不同包   

final的作用

1.final 修饰的类不可以被继承   
2.final 修饰的方法不可以被重写   
3.final 修饰的变量不可以被修改,只是引用不能被修改,引用的内容还是可以改的

java三大特性

1.封装:将一个对象内部进行隐藏通过修饰符,通过复用性和安全性   
2.继承:提高代码的复用性,是多态的前提  
3.多态:父类或者父接口可以引用子类的实例对象,提高灵活性  

抽象类和接口的对比

相同:  
1.抽象类和接口都不能实例化   
2.都是用来继承或者实现的  
3.都包含抽象方法,子类都需要重写覆盖  
    
不相同:  
1.关键字:抽象类abstract 接口 interface  
2.构造器:抽象类可以有构造器 接口不能有构造器  
3.方法修饰符: 抽象类可以是任意访问修饰符 接口方法只能并且默认就是public  
4.继承:类只可以继承一个抽象类, 类可以实现多个接口  
5.字段声明:抽象类可以是任意的, 接口只能或者默认是public static  

值传递和引用传递的区别

 值传递:方法传递参数,当为基本类型,那么是值传递,直接传递的是内容的拷贝,修改赋值不影响原来的值  
 引用传递:方法传递参数,当为引用类型,那么少是引用传递,直接拷贝是内存地址,修改引用内容对原来的值有影响  
 值和引用传递:本质上都是值传递,一个传递的是内容,一个传递的是地址(特殊内容),一个是内容拷贝,一个是地址拷贝,重新对这两种类型的参数赋值都不影响原来的变量  

String和StringBuffer、StringBuilder的区别

可变性:  
1.不可变:String对象是不可变的,底层的数据结构为 private final char[]  
2.可变: StringBuffer、StringBuilder 是可变的,底层的数据结构为 char[] value  
    
线程安全性  
1.线程安全的:StringBufferString是线程安全的,StringBuffer加了同步锁,String不可再次写只可读  
2.线程不安全的: StringBuilder线程不安全,没有进行同步   
    
使用方式   
1.少量字符串操作用String  
2.线程安全用StringBuffer  
3.线程不安全但是要效率用StringBuilder  

bio,nio,aio的区别

1.bio就是我们使用的传统io,读写阻塞,需要开单独线程处理,并发能力低   
2.nio就是bio的升级,也叫做非阻塞io,提供了Buffer,Channel,Selector的方式实现和操作io,实现多路复用并发负载能力高  
3.aio是nio2版本,也叫做异步非堵塞 io ,异步 io 的操作基于事件和回调机制。

hashCode和equals方法

1.在使用Hash相关类型集合的时候,HashSet,HashMap,在判断是不是一个对象的时候,
  是hashCode和equals方法同时返回true,才会认为是同一个对象,才会进行覆盖,否则当做一个新对象存储  
      
2.Long,Integer...这些基本类型都帮我们重写好了hashCode和equals方法,可以通过
 hashCode和equals方法唯一标识一个对象,我们可以直接使用不会有问题  
     
 3.我们自定义的类,会直接继承Object的hashCode方法,直接返回内存地址,那么直接new一个对象
   肯定hashCode不会相等,那么在使用HashSet,HashMap就永远都不是同一个对象  
       
 4.如果你定义的类不会用到Hash相关的集合操作,那么可以不重写hashCode和equals方法  
     
 5.使用了lombok插件的添加相关注解已经重写了hashCode和equals方法  

 public int hashCode() {
	        int PRIME = true;
	        int result = 1;
	        Object $userId = this.getUserId();
	        int result = result * 59 + ($userId == null ? 43 : $userId.hashCode());
	        Object $userName = this.getUserName();
	        result = result * 59 + ($userName == null ? 43 : $userName.hashCode());
	        Object $appName = this.getAppName();
	        result = result * 59 + ($appName == null ? 43 : $appName.hashCode());
	        return result;
	    }
	  public boolean equals(final Object o) {
	        if (o == this) {
	            return true;
	        } else if (!(o instanceof AccountCreateDto)) {
	            return false;
	        } else {
	            ......
        }

Hash相关集合使用String做Key的好处

```java
 使用String作为key的速度更快,因为比较hashCode的时候,String的不需要重写计算Hash,
 已经当做String对象的hash属性缓存下来了
 public int hashCode() {
    int h = hash;
    if (h == 0 && value.length > 0) {
        char val[] = value;

        for (int i = 0; i < value.length; i++) {
            h = 31 * h + val[i];
        }
        //缓存计算的hash值
        hash = h;
    }
    //如果有,直接返回
    return h;
}
```

常用的集合类

1.主要是两个接口 CollectionMap
  Collection子接口:Set, List,Queue
  Map接口:没有细分子接口   
      
2.常见实现
  List:ArrayListLinkedListStack,Vector
  Set:HashSetTreeSetLinkedHashSet
  Map:HashMapTreeMapHashtableConcurrentHashMap   
      
3.SetList,Map特性
  Set: 允许存入null,不允许重复
  List: 允许存入多个null,允许重复
  Map: 存储的是键值对,key可以为null,不允许重复key

ArrayList 和 LinkedList 的区别

1.ArrayList底层用的数组,LinkedList底层是双向链表   
    
2.ArrayList随机访问效率高,直接通过数组下标(O(1));LinkedList随机访问效率差点,需要移动指针(O(n))   
    
3.ArrayList添加/删除效率低,设计到扩容素组元素移动;LinkedList的插入删除直接改变指针的指向   
    
4.ArrayList 和 LinkedList 都是不同步的,也就是不保证线程安全

HashMap 与 HashTable 区别

1.HashMap非线程安全,HashTable线程安全   
   
2.HashMap的key可以为null,HashTable的key不能为null   
    
3.HashMap底层数据结构是数组+链表+红黑树,HashTable底层数据结构没做优化依然是数组+链表   
    
4.HashMap初始大小是16,扩容为2倍,HashTable初始大小是11,扩容2n+1