首页 > 编程语言 >2.Java基础【Java面试第三季】

2.Java基础【Java面试第三季】

时间:2023-05-21 19:06:54浏览次数:47  
标签:java String nums int 第三季 面试 intern 字符串 Java


2.Java基础【Java面试第三季】

  • 前言
  • 推荐
  • 2.Java基础
  • 01_字符串常量Java内部加载-上
  • 58同城的java字符串常量池
  • 面试code
  • 讲解
  • intern()方法---源码+解释
  • 02_字符串常量Java内部加载-下
  • why
  • OpenJDK8底层源码说明
  • 递推步骤
  • 总结
  • 考查点
  • 03_闲聊力扣算法第一题
  • 字节跳动两数求和
  • 题目说明
  • 面试题
  • 解法
  • 04_TwoSum暴力解法
  • 05_TwoSum优化解法
  • 考察点
  • 字节跳动手写LRU算法
  • 最后

前言

2023-2-1 13:23:19

推荐

Java开发常见面试题详解(LockSupport,AQS,Spring循环依赖,Redis)

2.Java基础

01_字符串常量Java内部加载-上

58同城的java字符串常量池

面试code

package javase;

public class StringPool58Demo1 {
    public static void main(String[] args) {
        String str1=new StringBuilder("58").append("tongchen").toString();
        System.out.println(str1.intern());
        System.out.println(str1 == str1.intern());

        System.out.println();

        String str2=new StringBuilder("ja").append("va").toString();
        System.out.println(str2);
        System.out.println(str2.intern());
        System.out.println(str2 == str2.intern());
    }
}

讲解

intern()方法—源码+解释

2.Java基础【Java面试第三季】_Java


由于运行时常量池是方法区的一部分,所以这两个区域的溢出测试可以放到一起进行。HotSpot从JDK 7开始逐步“去永久代”的计划,并在JDK 8中完全使用元空间来代替永久代的背景故事,在此我们就以测试代码来观察一下,使用"永久代"还是“元空间"来实现方法区,对程序有什么实际的影响。

String:intern()是一个本地方法,它的作用是如果字符串常量池中已经包含一个等于此String对象的字符串,则返回代表池中这个字符串的String对象的引用;否则,会将此String对象包含的字符串添加到常量池中,并且返回此String对象的引用。在JDK 6或更早之前的HotSpot虚拟机中,常量池都是分配在永久代中,我们可以通过-XX:PermSize和-XX:MaxPermSize限制永久代的大小,即可间接限制其中常量池的容量。

package javase;

public class StringPool58Demo1 {
    public static void main(String[] args) {
        String str1=new StringBuilder("58").append("tongchen").toString();
        System.out.println(str1.intern());
        System.out.println(str1 == str1.intern());

        System.out.println();

        String str2=new StringBuilder("ja").append("va").toString();
        System.out.println(str2);
        System.out.println(str2.intern());
        System.out.println(str2 == str2.intern());
    }
}

输出结果:

58tongchen
58tongchen
true

java
java
false

02_字符串常量Java内部加载-下

why
  • 按照代码结果,Java字符串答案为false,必然是两个不同的java,那另外一个java字符串如何加载进来的?
  • 为什么
  • 有一个初始化的Java字符串(JDK出娘胎自带的),在加载sun.misc.Version这个类的时候进入常量池。

OpenJDK8底层源码说明

递推步骤
  • System代码解析 System -> initializeSystemClass() -> Version

System

package java.lang;

public final class System {

    /* register the natives via the static initializer.
     *
     * VM will invoke the initializeSystemClass method to complete
     * the initialization for this class separated from clinit.
     * Note that to use properties set by the VM, see the constraints
     * described in the initializeSystemClass method.
     */
    private static native void registerNatives();
    static {
        registerNatives();
    }
    
    //本地方法registerNatives()将会调用initializeSystemClass()
    private static void initializeSystemClass() {

		...
        
        sun.misc.Version.init();

		...
    }
    ...
}

Version

package sun.misc;

//反编译后的代码
public class Version {
	private static final String launcher_name = "java";
	...
}

测试Version的其他字符串

public class Version {
    private static final java.lang.String launcher_name = "java";
    private static final java.lang.String java_version = "1.8.0_60";
    private static final java.lang.String java_runtime_name = "Java(TM) SE Runtime Environment";
    private static final java.lang.String java_profile_name = "";
    private static final java.lang.String java_runtime_version = "1.8.0_60-b27";
}
String str3 =new StringBuilder("1.8.0_60").toString();
        String str4 =new StringBuilder("Java(TM) SE Runtime Environment").toString();
        String str5 =new StringBuilder("").toString();
        String str6 =new StringBuilder("1.8.0_60-b27").toString();

        System.out.println(str3 == str3.intern()||str4 == str4.intern()
        ||str5==str5.intern()||str6==str6.intern());//false
  • 类加载器和rt.jar----根加载器提前部署加载rt.jar
  • 2.Java基础【Java面试第三季】_System_02

  • OpenJDK8源码
总结

《深入理解java虚拟机》----第二章 Java内存区域与内存溢出异常----2.4 实战:OutOfMemoryError异常----2.4.3 方法区和运行时常量池溢出----代码清单2-8 String.intern()返回引用的测试

这段代码在JDK 6中运行,会得到两个false,而在JDK 7中运行,会得到一个true和一个false。产生差异的原因是,在JDK 6中,intern()方法会把首次遇到的字符串实例复制到永久代的字符串常量池中存储,返回的也是永久代里面这个字符串实例的引用,而由StringBuilder创建的字符串对象实例在Java堆上,所以必然不可能是同一个引用,结果将返回false。

而JDK 7(以及部分其他虚拟机,例如JRockit)的intern()方法实现就不需要再拷贝字符串的实例到永久代了,既然字符串常量池已经移到Java堆中,那只需要在常量池里记录一下首次出现的实例引用即可,因此intern()返回的引用和由StringBuilder创建的那个字符串实例就是同一个。而对str2比较返回false,这是因为“java”这个字符串在执行StringBuilder.toString()之前就已经出现过了,字符串常量池中已经有它的引用,不符合intern()方法要求“首次遇到"”的原则,“计算机软件"这个字符串则是首次出现的,因此结果返回true。
sun.misc.Version类会在JDK类库的初始化过程中被加载并初始化,而在初始化时它需要对静态常量字段根据指定的常量值(ConstantValue〉做默认初始化,此时被sun.misc.Version.launcher静态常量字段所引用的"java"字符串字面量就被intern到HotSpot VM的字符串常量池——StringTable里了。

sun.misc.Version类会在JDK类库的初始化过程中被加载并初始化,而在初始化时它需要对静态常量字段根据指定的常量值(ConstantValue〉做默认初始化,此时被sun.misc.Version.launcher静态常量字段所引用的"java"字符串字面量就被intern到HotSpot VM的字符串常量池——StringTable里了。

考查点

  • intern()方法,判断true/false?
  • 《深入理解java虚拟机》书原题是否读过经典JVM书籍
03_闲聊力扣算法第一题

字节跳动两数求和

然后考了2个算法:
1给定一个数m,求大干该数的最小2的n次幂、返同n	这个我一分钟内就完成了。
2.leetCode的第i题
给定一个整数数组nums和一个目标值 target,请你在该数组中找出和为目标值的那两个整数,并返回他们的数组下标。
你可以假设每种输入只会对应一个答案。但是,数组中同一个元素不能使用两遍。示例:
输入:nums = [2,7,11,15], target = 9
输出:[0,1]
解释:因为 nums[0] + nums[1] == 9 ,返回 [0, 1] 。
快手算法:
给定一个链表,.删除相邻相同的数据项。比如2 -〉2-〉3 返回 2-〉3。这个算法也没运行出来,但是之前题目打的比较好,一面过了。
给定一个链表,"其中元素只有0和1,删除0的节点,并返回链表。≤(后来面试官说这是AQS的一部分源码……)

题目说明

https://leetcode.cn/problems/two-sum/

2.Java基础【Java面试第三季】_面试_03

面试题

package javase;

import java.util.HashMap;

/**
 * 给定一个整数数组nums和一个目标值 target,请你在该数组中找出和为目标值的那两个整数,并返回他们的数组下标。
 * 你可以假设每种输入只会对应一个答案。但是,数组中同一个元素不能使用两遍。示例:
 * 输入:nums = [2,7,11,15], target = 9
 * 输出:[0,1]
 * 解释:因为 nums[0] + nums[1] == 9 ,返回 [0, 1] 。
 */
public class TwoSumDemo2 {
    public int[] twoSum(int[] nums, int target) {
        return null;
    }
    public static void main(String[] args) {
        int[] nums=new int[]{2,7,11,15};
        int target=9;

    }
}

解法

  • 暴力
04_TwoSum暴力解法
package javase;

import java.util.Arrays;
import java.util.HashMap;

/**
 * 给定一个整数数组nums和一个目标值 target,请你在该数组中找出和为目标值的那两个整数,并返回他们的数组下标。
 * 你可以假设每种输入只会对应一个答案。但是,数组中同一个元素不能使用两遍。示例:
 * 输入:nums = [2,7,11,15], target = 9
 * 输出:[0,1]
 * 解释:因为 nums[0] + nums[1] == 9 ,返回 [0, 1] 。
 */
public class TwoSumDemo2 {

    //遍历-->暴力破解
    /**
     * 通过双重循环遍历数组中所有元素的两两组合,
     * 当出现符合的和的返回两个元素的下标
     * @param nums
     * @param target
     * @return
     */
    public static int[] twoSum1(int[] nums, int target) {
        for (int i = 0; i < nums.length; i++) {
            for (int j = i+1; j <nums.length-1 ; j++) {
                if (target-nums[i]==nums[j]){
                    return new int[]{i,j};
                }
            }
        }
        return null;
    }
   
    
    public static void main(String[] args) {
        int[] nums=new int[]{2,7,11,15};
        int target=9;

        System.out.println(Arrays.toString(twoSum1(nums, target)));

    }
}

还有没有更优的解法

05_TwoSum优化解法
  • 哈希
package javase;

import java.util.Arrays;
import java.util.HashMap;

/**
 * 给定一个整数数组nums和一个目标值 target,请你在该数组中找出和为目标值的那两个整数,并返回他们的数组下标。
 * 你可以假设每种输入只会对应一个答案。但是,数组中同一个元素不能使用两遍。示例:
 * 输入:nums = [2,7,11,15], target = 9
 * 输出:[0,1]
 * 解释:因为 nums[0] + nums[1] == 9 ,返回 [0, 1] 。
 */
public class TwoSumDemo2 {

    //遍历-->暴力破解

    /**
     * 通过双重循环遍历数组中所有元素的两两组合,
     * 当出现符合的和的返回两个元素的下标
     * @param nums
     * @param target
     * @return
     */
    public static int[] twoSum1(int[] nums, int target) {
        for (int i = 0; i < nums.length; i++) {
            for (int j = i+1; j <nums.length-1 ; j++) {
                if (target-nums[i]==nums[j]){
                    return new int[]{i,j};
                }
            }
        }
        return null;
    }
    
    public static int[] twoSum2(int[] nums, int target) {
        HashMap<Integer,Integer> map=new HashMap();
        for (int i = 0; i < nums.length; i++) {
            if (map.containsKey(target-nums[i])){
                return new int[]{map.get(target-nums[i]),i};
            }
            
            map.put(nums[i],i);
            
        }

        return null;
    }

    public static void main(String[] args) {
        int[] nums=new int[]{2,7,11,15};
        int target=9;

        System.out.println(Arrays.toString(twoSum1(nums, target)));
        System.out.println(Arrays.toString(twoSum2(nums, target)));

    }
}

考察点

你都想来大厂了,算法居然从来没有刷过?呵呵机会偏爱有准备有实力的头脑,不是白说的…

字节跳动手写LRU算法

见Redis最后(请坚持到最后一章)

最后

2023-2-1 14:56:19

这篇博客能写好的原因是:站在巨人的肩膀上

这篇博客要写好的目的是:做别人的肩膀

开源:为爱发电

学习:为我而行




标签:java,String,nums,int,第三季,面试,intern,字符串,Java
From: https://blog.51cto.com/u_15719556/6319996

相关文章

  • java中使用jep调用python类
    经过调研,目前这应该只有一种调用方式了,那就是使用jep,后来亲测了以下确实是可行,我是使用jep调用了一个python文件中的类,并测试了类的一个方法,可以正常执行,但是具体速度会不会慢很多,我还没有测试。刚开始在调研的时候,说jython也可以调用,但是这个包只支持2.7python,毕竟现在很少有用2......
  • IDEA——Java的一些依赖
    <!--导入knife4j的maven坐标(Swagger框架)--><dependency><groupId>com.github.xiaoymin</groupId><artifactId>knife4j-spring-boot-starter</artifactId><version>3.0.2</ve......
  • Android 教你一步步搭建MVP+Retrofit+RxJava网络请求框架
    1.什么是MVP? MVP(ModelViewPresenter)其实就是一种项目的整体框架,能让你的代码变得更加简洁,说起框架大家可能还会想到MVC、MVVM。由于篇幅原因,这里我们先不讲MVVM,先来看一下MVC。其实Android本身就采用的是MVC(ModelViewControllor)模式、其中Model指的是数据逻辑和实体模型......
  • JavaSE的简单了解
    JavaSE简称为JavaStandardEdition,是Java编程语言的基础平台。JavaSE提供了一系列用于开发Java应用程序的API和工具,以及Java虚拟机(JVM)和编译器。JavaSE是Java技术生态系统的核心,是Java应用程序开发的基础。 编译执行过程数据类型分类 JavaSE框架包括以下部分:......
  • JavaSE的简单了解
    JavaSE简称为JavaStandardEdition,是Java编程语言的基础平台。JavaSE提供了一系列用于开发Java应用程序的API和工具,以及Java虚拟机(JVM)和编译器。JavaSE是Java技术生态系统的核心,是Java应用程序开发的基础。 编译执行过程数据类型分类 JavaSE框架包括以下部分:......
  • Java面向对象中“匿名对象”的使用
    1.0匿名对象的基本知识匿名对象顾名思义,匿名对象指的就是没有名字的对象,在使用中理解为实例化一个类对象,但是并不把它赋给一个对应的类变量,而是直接使用。在理解匿名对象前,我们先创建一个类便于后面的使用。匿名对象具有以下特征:语法上:只创建对象,但不用变量来接收,例如:假设现......
  • 经典面试题
    TC经典面试题1.赛马问题WY经典面试题2.:烧香问题砝码称重问题有36匹马,6个跑道,在没有计时器的情况下,至少需要赛马多少次,才能比出前三名?答案:至少需要比较8次。解题思路:先把36匹马平均分成6组,假设为A,B,C,D,E,F,让每组的马赛跑一次,假设各组的名次分别为A1>A2>A3>A4>A5>A6,其他组也是如此,决......
  • java list.stream 多条件去重(分组)
    List<EmEventConfigPointExcelDto>listNew=list.stream().collect(Collectors.collectingAndThen(Collectors.toCollection(()->newTreeSet<>(Comparator.comparing((o)-......
  • java基于springboot+vue的土特产在线销售平台、特产在线销售商城,附源码+数据库+lw文档
    1、项目介绍考虑到实际生活中在藏区特产销售管理方面的需要以及对该系统认真的分析,将系统权限按管理员和用户这两类涉及用户划分。(1)管理员功能需求管理员登陆后,主要模块包括首页、个人中心、用户管理、特产信息管理、特产分类管理、特产分类管理、特产评分管理、系统管理、订单......
  • JavaScript学习笔记:模块
    前言在js编程中,模块指的是按照一定格式将代码以功能拆分后作为独立文件存在的一个实体。早期的JS并没有规定模块应该如何设计,核心语言也没有针对模块提供相关支持。早期的代码使用IIFE来实现一个模块,它是通过向全局对象添加属性来实现与其他模块来交互的。(function(){v......