周末面试题又来了

周末面试题又来了

码个蛋(codeegg) 第 836 次推文

码妞看世界

周末面试题又来了

1. Android10新特性及适配

  • 新特性:
    1) 折叠屏
    2) 5G网络支持
    3) 智能答复通知
    4) 暗黑模式
    5) 手势导航
    6) 浮动设置面板
    7) 分享改进

  • 隐私
    1) 前台访问权限
    2) 网络扫描需要精确位置权限
    3) 防止设备跟踪
    4) 保护外部存储中的用户数据
    5) 阻止不需要的中断

  • 安全
    1) 存储加密
    2) 默认TLS1.3
    3) 平台优化
    4) 改进的生物识别

  • 相机和媒体
    1) 照片动态深度
    2) 音频播放捕获
    3) 新的音视频编解码器
    4) 原生MIDI API
    5) 定向可缩放的麦克风
    6) 无处不在的Vulkan

  • 连接优化
    1) 改进的点对点和互联网连接
    2) WiFi高性能模式

  • Android系统基础
    1) ART优化
    2) 神经网络API1.2
    3) 热感API
    4) 公共API的兼容性

更快的更新速度,更新鲜的代码~

2. get 和 post 请求有哪些区别

  1. GET 请求的数据会附在 URL 之后(就是把数据放置在 HTTP 协议头中),以?分割 URL 和传输数据,参数之间以&相连,如: login.action?name=zhagnsan&password=123456。

    POST 把提交的数据则放置在是 HTTP 包的包体中。

  2. GET 方式提交的数据最多只能是 1024 字节,理论上 POST 没有限制,可传较大量的数据。其实这样说是错误 的,不准确的:


    “GET 方式提交的数据最多只能是 1024 字节",因为 GET 是通过 URL 提交数据,那么 GET 可提交的数据量就跟 URL 的长度有直接关系了。而实际上,URL 不存在参数上限的问题,HTTP 协议规范没有对 URL 长度进行限制。这个 限制是特定的浏览器及服务器对它的限制。IE 对 URL 长度的限制是 2083 字节(2K+35)。对于其他浏览器,如 Netscape、 FireFox 等,理论上没有长度限制,其限制取决于操作系统的支持。

  3. POST 的安全性要比 GET 的安全性高。

    注意: 这里所说的安全性和上面 GET 提到的“安全”不是同个概念。上面“安全”的含义仅仅是不作数据修改,而这里安全的含义是真正的 Security 的含义,比如: 通过 GET 提交数据,用 户名和密码将明文出现在 URL 上,因为(1)登录页面有可能被浏览器缓存,(2)其他人查看浏览器的历史纪录,那么别 人就可以拿到你的账号和密码了,除此之外,使用 GET 提交数据还可能会造成 Cross-site request forgery 攻击。

3. 线程和进程的区别? 为什么不仅仅用进程?

  • 进程:

进程是具有独立功能的程序关于某个数据集合上的一次运行活动,是系统进行资源分配和调度(若不支持线程机制,进程的系统调度的单位。否则,线程是系统调度的单位)的独立单位。

  • 特点:

一、进程是程序的一次执行过程。若程序执行两次甚至多次,则需要两个甚至多个进程。

二、进程是正在运行程序的抽象。它代表运行的CPU,也称进程是对CPU的抽象。

三、系统资源(如内存、文件)以进程为单位分配。

四、操作系统为每个进程分配了独立的地址空间。

五、操作系统通过“调度”把控制权交给进程。

  • 进程的弊端:

一、进程切换的代价、开销比较大。

二、在一个进程内也需要并行执行多个程序,实现不同的功能。

三、进程有时候性能比较低。(线程的引入为了解决进程的弊端)。

  • 线程:

一、有标识符ID。

二、有状态及状态转换,所以需要提供一些状态转换操作。

三、不运行时需要保存上下文环境,所以需要程序计数器等寄存器。

四、有自己的栈和栈指针。

五、共享所在进程的地址空间和其它资源。

周末面试题又来了

  • 总结:

一、进程是程序在某个数据集合上的一次运行活动;线程是进程中的一个执行路径。(进程可以创建多个线程)。

二、在支持线程机制的系统中,进程是系统资源分配的单位,线程是CPU调度的单位。三、进程之间不能共享资源,而线程共享所在进程的地址空间和其它资源。同时线程还有自己的栈和栈指针,程序计数器等寄存器。

四、进程有自己独立的地址空间,而线程没有,线程必须依赖于进程而存在。

五、进程切换的开销较大。线程相对较小。(前面也提到过,引入线程也出于了开销的考虑)。

4. Java对象的生命周期

1、创建阶段(Created):

在创建阶段系统通过下面的几个步骤来完成对象的创建过程;

一、为对象分配存储空间。

二、开始构造对象。

三、从超类到子类对static成员进行初始化。

四、超类成员变量按顺序初始化,递归调用超类的构造方法。

五、子类成员变量按顺序初始化,子类构造方法调用。一旦对象被创建,并被分派给某些变量赋值,这个对象的状态就切换到了应用阶段。

2、应用阶段(In Use):

对象至少被一个强引用持有。

3、不可见阶段(Invisible):

当一个对象处于不可见阶段时,说明程序本身不再持有该对象的任何强引用,虽然该这些引用仍然是存在着的。简单说就是程序的执行已经超出了该对象的作用域了。

4、不可达阶段(Unreachable):

对象处于不可达阶段是指该对象不再被任何强引用所持有。与“不可见阶段”相比,“不可见阶段”是指程序不再持有该对象的任何强引用,这种情况下,该对象仍可能被JVM等系统下的某些已装载的静态变量或线程或JNI等强引用持有着,这些特殊的强引用被称为”GC root”。存在着这些GCroot会导致对象的内存泄露情况,无法被回收。

5、收集阶段(Collected):

当垃圾回收器发现该对象已经处于“不可达阶段”并且垃圾回收器已经对该对象的内存空间重新分配做好准备时,则对象进入了“收集阶段”。如果该对象已经重写了finalize()方法,则会去执行该方法的终端操作。

这里要特别说明一下:不要重载finazlie()方法!

原因有两点:

一、会影响JVM的对象分配与回收速度 在分配该对象时,JVM需要在垃圾回收器上注册该对象,以便在回收时能够执行该重载方法;在该方法的执行时需要消耗CPU时间且在执行完该方法后才会重新执行回收操作,即至少需要垃圾回收器对该对象执行两次GC。

二、可能造成该对象的再次“复活”在finalize()方法中,如果有其它的强引用再次持有该对象,则会导致对象的状态由“收集阶段”又重新变为“应用阶段”。这个已经破坏了Java对象的生命周期进程,且“复活”的对象不利用后续的代码管理。

6、终结阶段:

当对象执行完finalize()方法后仍然处于不可达状态时,则该对象进入终结阶段。在该阶段是等待垃圾回收器对该对象空间进行回收。

7、对象空间重新分配阶段:

垃圾回收器对该对象的所占用的内存空间进行回收或者再分配了,则该对象彻底消失了,称之为“对象空间重新分配阶段”。

5. 为什么等待和通知是在 Object 类而不是 Thread 中声明的

一个棘手的 Java 问题,如果 Java编程语言不是你设计的,你怎么能回答这个问题呢?Java编程的常识和深入了解有助于回答这种棘手的 Java 核心方面的面试问题。

周末面试题又来了

为什么 waitnotifynotifyAll 是在 Object 类中定义的而不是在 Thread 类中定义
这是有名的 Java 面试问题,招2~4年经验的到高级 Java 开发人员面试都可能碰到。

这个问题的好在它能反映了面试者对等待通知机制的了解,以及他对此主题的理解是否明确。就像为什么 Java 中不支持多继承或者为什么 String 在 Java 中是 final 的问题一样,这个问题也可能有多个答案。

为什么在 Object 类中定义 wait 和 notify 方法,每个人都能说出一些理由。从我的面试经验来看,wait 和 nofity 仍然是大多数Java 程序员最困惑的,特别是2到3年的开发人员,如果他们要求使用 wait 和 notify, 他们会很困惑。因此,如果你去参加 Java 面试,请确保对 wait 和 notify 机制有充分的了解,并且可以轻松地使用 wait 来编写代码,并通过生产者-消费者问题或实现阻塞队列等了解通知的机制。

周末面试题又来了

为什么等待和通知需要从同步块或方法中调用, 以及 Java 中的 wait,sleep 和 yield 方法之间的差异,如果你还没有读过,你会觉得有趣。为何 wait,notify 和 notifyAll 属于 Object 类? 为什么它们不应该在 Thread 类中? 以下是我认为有意义的一些想法:

  1. wait 和 notify 不仅仅是普通方法或同步工具,更重要的是它们是 Java 中两个线程之间的通信机制对语言设计者而言, 如果不能通过 Java 关键字(例如 synchronized)实现通信此机制,同时又要确保这个机制对每个对象可用, 那么 Object 类则是的正确声明位置。记住同步和等待通知是两个不同的领域,不要把它们看成是相同的或相关的。同步是提供互斥并确保 Java 类的线程安全,而 wait 和 notify 是两个线程之间的通信机制。

  2. 每个对象都可上锁,这是在 Object 类而不是 Thread 类中声明 wait 和 notify 的另一个原因。(大家平等)

  3. 在 Java 中为了进入代码的临界区,线程需要锁定并等待锁定,他们不知道哪些线程持有锁,而只是知道锁被某个线程持有, 并且他们应该等待取得锁, 而不是去了解哪个线程在同步块内,并请求它们释放锁定。

  4. Java 是基于 Hoare 的监视器的思想。在Java中,所有对象都有一个监视器。
    线程在监视器上等待,为执行等待,我们需要2个参数:

  • 一个线程

  • 一个监视器(任何对象)

在 Java 设计中,线程不能被指定,它总是运行当前代码的线程。但是,我们可以指定监视器(这是我们称之为等待的对象)。这是一个很好的设计,因为如果我们可以让任何其他线程在所需的监视器上等待,这将导致“入侵”,导致在设计并发程序时会遇到困难。请记住,在 Java 中,所有在另一个线程的执行中侵入的操作都被弃用了(例如 stop 方法)。

往期文章:

今日问题:

最近复习了啥?

周末面试题又来了

专属升级社区:《这件事情,我终于想明白了》 

周末面试题又来了