2021-春招-锅巴

int和Integer有什么区别?

https://blog.csdn.net/chenliguan/article/details/53888018

Java 提供两种不同的类型:引用类型和原始类型(或内置类型)。Int是java的原始数据类型,Integer是java为int提供的封装类。

  • 原始类型:boolean,char, byte, short, int, long,float,double
    原始类型直接存储在Java的内存栈中,
  • 包装类型:Boolean,Character, Byte,Short,Integer,Long,Float,Double

基本使用对比

  • Integer是int的包装类;int是基本数据类型;
  • Integer变量必须实例化后才能使用;int变量不需要;
  • Integer实际是对象的引用,指向此new的Integer对象;int是直接存储数据值 ;
  • Integer的默认值是null;int的默认值是0。
//两个通过new生成的Integer变量永远是不相等的。因为new生成的是两个对象,其内存地址不同

Integer i = new Integer(100);
int j = 100;
System.out.print(i == j); //true
// 自动拆箱Integer为int,故变为数值比较
//===========================================================================
Integer i = new Integer(100);//指向堆中新建的对象
Integer j = 100;	//指向的是静态常量池中cache数组中存储的指向了堆中的Integer对象
System.out.print(i == j); //false,内存中对象的引用地址不同
//===========================================================================
Integer i = 100; //等价于:Integer i = Integer.valueOf(100)
Integer j = 100;
System.out.print(i == j); //true,
//java API中对Integer类型的valueOf:对于-128到127之间的数,会进行缓存,下次使用时,直接从缓存中取出,并没有new 新对象
Integer i = 128;
Integer j = 128;
System.out.print(i == j); //false

//===========================================================================
Integer num = 9;//自动装箱,Integer num = Integer.valueOf(9);
num--;	//自动拆箱,Integer对象不能直接进行运算,转换为基本类型

-128~+127之间的数据会缓存,归结于java对于Integer与int的自动装箱与拆箱的设计,是一种模式:叫享元模式(flyweight)。

  1. 加大对简单数字的重利用,-128~127之内的数值,被装箱为Integer对象后,会存在内存中被重用,始终只存在一个对象。

    -128~127存储在:静态常量池,static final cache[];cache[i]=new Integer(num);该static final类型数组cache中存放的数据却是Integer类型(即指向堆中的Integer对象,是个引用地址)
    
  2. 而如果在-128~127之外的数,装箱时都新建一个 Integer对象。

什么是值传递和引用传递?

https://blog.csdn.net/Pit3369/article/details/108704526

形参

实参

值传递:不是简单的把实参传递给形参,而是,实参在栈内建立了一个副本,然后把副本传递给了形参。

引用传递:一般对于对象型变量而言。特别注意传递String等包装类型时。User对象存放在堆,其引用user存放在栈。函数调用时,参数传递user给temp,即:创建user引用的副本temp,这俩引用都指向堆中的User对象,故修改user或temp,都会对堆中USER对象产生影响。

==与equlas有什么区别?

https://www.jianshu.com/p/9cbed9f33a4d

equals 是方法,而 == 是操作符;

基本类型变量的比较,使用 == 比较, 一般比较的是它们的值

引用类型的变量来说(例如 String 类)才有 equals 方法,因为 String 继承了 Object 类, equals 是 Object 类的通用方法。默认不重写equlas方法下,比较对象在内存中存放的地址。但是,若重写了equlas方法,如String类的equlas()则比较值是否相等。

// Object 类的 equals 方法,本质就是==
public boolean equals(Object obj) {
  return (this == obj);
}

//String 类中的 equals 方法
@Override 
public boolean equals(Object other) {
  if (other == this) {	//内存的存放地址相等时,直接返回true
    return true;
  }
  if (other instanceof String) {	
      //内存地址不等时,判断存放的字符串内容
      ......
  } else {
      return false;
  }
}

String a = "Hello World";
String b = new String("Hello World");
String c = b; //引用传递
System.out.println("a == b:" + a == b);             //false,a存在常量池;b在堆中,内存地址不等
System.out.println("b == c:" + b == c);             //true,bc为同个内存地址
System.out.println("a == c:" + a == c);             //false,
System.out.println("a.equals(b):" + a.equals(b));   //true,内存不等时,比较字符串内容
System.out.println("b.equals(c):" + b.equals(c));   //true
System.out.println("a.equals(c):" + a.equals(c));   //true

final关键字

https://juejin.cn/post/6844903667494027271

final变量

作为类常量static final必须在声明时初始化,JVM将其缓存在常量池中,在读取变量时不会加载该类


public class Main {
    public static final int i = 2;
    Main() {
        System.out.println("调用构造函数"); // 该方法不会调用
    }
    public static void main(String[] args) {
        System.out.println(Main.i);
    }
}

final方法

表示该方法不能被子类的方法重写

final类

final类不能被继承,final类中的方法默认也会是final类型的,java中的String类和Integer类都是final类型的。

  1. final成员变量必须在声明的时候初始化或者在构造器中初始化,否则就会报编译错误。final变量一旦被初始化后不能再次赋值。
  2. 本地变量必须在声明时赋值。 因为没有初始化的过程
  3. 在匿名类中所有变量都必须是final变量。
  4. final方法不能被重写, final类不能被继承
  5. 接口中声明的所有变量本身是final的。类似于匿名类
  6. final和abstract这两个关键字是反相关的,final类就不可能是abstract的。
  7. final方法在编译阶段绑定,称为静态绑定(static binding)。
  8. 将类、方法、变量声明为final能够提高性能,这样JVM就有机会进行估计,然后优化。

好处

  1. 提高了性能,JVM在常量池中会缓存final变量
  2. final变量在多线程中并发安全,无需额外的同步开销
  3. final方法是静态编译的,提高了调用速度
  4. final类创建的对象是只可读的,在多线程可以安全共享

抽象类和接口的区别

https://www.jianshu.com/p/038f0b356e9a

抽象类

  • 如果一个类没有包含足够多的信息来描述一个具体的对象,这样的类就是抽象类。
  • 抽象类在实际应用中,更多的是因为类中有抽象方法。抽象方法:只声明,不实现。具体的实现由继承它的子类来实现。实际点就是:被abstract修饰的方法,只有方法名没有方法实现,具体的实现要由子类实现。
  • 一个类中含有抽象方法(被abstract修饰),那么这个类必须被声明为抽象类(被abstract修饰)。

接口

  • 接口在java中是一个抽象类型,是抽象方法的集合。一个类通过继承接口的方式,从而继承接口的抽象方法。

  • 实现某个接口的类必须在类中实现该接口的全部方法。虽然接口内的方法都是抽象的(和抽象方法很像,没有实现)但是不需要abstract关键字。

  • 接口中没有构造方式(因为接口不是类)、接口中的方法必须是抽象的(不能实现)、接口中除了static、final变量,不能有其他变量、接口支持多继承(一个类可以实现多个接口)

抽象类中可以有已经实现了的方法,也可以有被abstract修饰的方法(抽象方法),因为存在抽象方法,所以该类必须是抽象类。

接口要求只能包含抽象方法,抽象方法是指没有实现的方法。

  • 抽象类使用extends关键字来继承抽象类。如果子类不是抽象类的话,它需要提供抽象类中所有声明的方法的实现。

    子类使用关键字implements来实现接口。它需要提供接口中所有声明的方法的实现。

抽象类可以有构造器,而接口不能有构造器

抽象类终究也是类,虽说不能实例化,但包括类的构造方法=构造器。接口是所有抽象方法的集合,注意,是集合,不是类,当然没有构造方法一说

java中抽象类只有单继承,接口就可以实现多继承。

抽象类可以直接添加新方法;接口中添加方法,还必须得在实现接口的类中继续添加新方法

因为抽象类可以存在非抽象方法,即默认实现。

Java提供和支持创建抽象类和接口。它们的实现有共同点,不同点在于:
接口中所有的方法隐含的都是抽象的。而抽象类则可以同时包含抽象和非抽象的方法。
类可以实现很多个接口,但是只能继承一个抽象类
类可以不实现抽象类和接口声明的所有方法,当然,在这种情况下,类也必须得声明成是抽象的。
抽象类可以在不提供接口方法实现的情况下实现接口。
Java接口中声明的变量默认都是final的。抽象类可以包含非final的变量。
Java接口中的成员函数默认是public的。抽象类的成员函数可以是private,protected或者是public。
接口是绝对抽象的,不可以被实例化。抽象类也不可以被实例化,如果它包含main方法的话是可以被调用的。
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值