写在前面

感觉其实字节对于语言本身并没有很多的涉及

这里就省去了一些我简历上的问题,也就是深挖项目。

笔试

一面

epoll、select、poll 区别

用户空间拷贝到内核空间FD_SETSIZE数组实现
pollfd结构 链表实现
epoll_ctl系统调用红黑树

epoll 的水平触发和边缘触发的区别

Edge Triggered (ET) 边沿触发:

  1. socket 的接收缓冲区状态变化时触发读事件,即空的接收缓冲区刚接收到数据时触发读事件。
  2. socket 的发送缓冲区状态变化时触发写事件,即满的缓冲区刚空出空间时触发读事件。
  3. 仅在缓冲区状态变化时触发事件。

Level Triggered (LT) 水平触发:

不为空不满可以继续写入数据

TCP 的流量控制

发送方把数据发得过快来不及接收
滑动窗口机制准确地控制发送字节数。

为什么有了流量控制还要有拥塞控制?

流量控制是避免发送方的数据填满接收方的缓存,但并不知道网络中发生了什么。

时延丢失重传数据更大的延迟以及更多的丢包

控制的目的就是避免发送方的数据填满整个网络。为了在发送方调节所要发送数据的数据量,定义了⼀个叫做「拥塞窗口」的概念。拥塞窗口 cwnd 是发送方维护的⼀个的状态变量,它会根据网络的拥塞程度动态变化的。

TCP 不是可靠传输吗?为什么会丢包呢?

TCP的可靠传输是会在丢包的时候进行重传,来形成可靠的传输,丢包这是网络的问题,而不是TCP机制的问题。

那你介绍一下拥塞控制的算法?

拥塞控制一共有四个算法:

发送方每收到⼀个 ACK,拥塞窗⼝ cwnd 的大小就会加 1慢启动门限 ssthresh 发送三次前⼀个包的ACK收到 3 个重复的 ACK 

进程、线程的区别

进程线程
系统中正在运行的一个应用程序系统分配处理器时间资源的基本单元
程序一旦运行就是进程进程之内独立执行的一个单元执行流
资源分配的最小单位程序执行的最小单位
独立的地址空间保护模式下不会对其它进程产生影响
没有单独的地址空间进程切换要求同时进行并且又要共享某些变量的并发操作,只能用线程,不能用进程

Go里面GMP模型是怎么样的?

可以重用
逻辑处理单元P 和 M 的这种关系就相当于 Linux 系统中的用户层面的线程和内核的线程是一样的
GMP模型

算法:旋转矩阵,牛客上写过,easy,秒

二面

上来就一个算法,结束又一个算法,难受。。

如何用栈实现队列

我们可以通过切片来模拟出队列。 只需要完成简单的 push,pop,再判断是否为空即可!

如何判断一个链表有没有环?

  1. 用hash来判断是否存在相同的值,也就是环。
  2. 快慢指针:快指针走两步,慢指针走一步,最终会相遇。

那为什么快慢指针一定能够相遇?

快指针出现在慢指针后面快指针往前走两步、慢指针往前走一步快指针往前走两步、慢指针往前走一步
  • 快慢指针第一次相遇的时候,慢指针少走了多少?
环形

我们设从起点到 X 点的距离是 x,因此当在第一次相遇的时候,在n点,慢指针的路程是 x+n ,而因为快指针的速度是慢指针的一倍,它们从头开始,运动时间就是完全一致的,因此当二者发生相遇的时候,有如下几点值得注意:

2 * ( x + n )x+2n
 x+n2*(x+n)x+n所以慢指针少走了环巡距离的一倍。

你用的是 mysql 是吧,那 B树 和 B+树 的区别是?

B 树

B+树

B+数结构
log (n)O(1)相近的数据预读进内存空间局部性外部存储

介绍一下死锁产生的必要条件

互斥条件,请求和保持条件,不剥夺条件,环路等待条件。

如何实现互斥锁?

有阻塞和唤醒功能
  1. 需要有一个标记锁状态的 state 变量。
  2. 需要记录哪个线程持有了锁。
  3. 需要有一个队列维护所有的线程。

如何实现自旋锁?

当时真不会,只磕磕绊绊说了一些自旋锁的东西。。

大家可以看这篇博客

算法:三数之和。秒

三面

kafka 和 其他消息队列,比如 rocketmq,rabbitmq ,有什么优势?

kafka 具备非常高可靠的分布式架构,功能简单,只支持一些主要的MQ功能,像一些消息查询,消息回溯等功能没有提供。时效是在ms级别以内的。

kafka如何保证消息不丢失?

那我们可以从两个方面也就是生产者,消费者以及 broker ,来说说

 send 方法网络问题并没有发送过去同步发送消息方法Future对象get() Producer 的 retries(重试次数)自动重试消息发送,避免消息丢失重试间隔当消费者拉取到了分区的某个消息之后,消费者会自动提交了 offsetenable.auto.commit设置为false自动提交 offset 手动提交 offset 将producer设置 acks = all 

https为什么是安全的?

因为 https 是基于 ssl 和 tls 加密而成的,https 的 s 就代表 ssl 和 tls。

ssl/tls 是怎么保证安全的?经过几次握手?

经过四次握手,客户端向服务器端索要并验证公钥,双方协商生成"对话密钥",双方采用"对话密钥"进行加密通信。 四次握手主要是交换以下信息:

  1. 数字证书:该证书包含了公钥等信息,一般是由服务器发给客户端,接收方通过验证这个证书是不是由信赖的CA签发,或者与本地的证书相对比,来判断证书是否可信;假如需要双向验证,则服务器和客户端都需要发送数字证书给对方验证;
  2. 三个随机数:这三个随机数构成了后续通信过程中用来对数据进行对称加密解密的“对话密钥”。
提到的证书发给客户端数字证书的公钥进行非对称加密在此之后的通信都是使用这个“对话密钥”来进行对称加密解密私钥没有被泄露
  1. 加密通信协议:就是双方商量使用哪一种加密方式,假如两者支持的加密方式不匹配,则无法进行通信;
SSL握手

事务的四大特性?

原子性、隔离性、一致性、持久性

用过哪些排序?

快排,堆排,归并比较常用。

快排一定最快吗?

不一定,当待排序的序列已经有序,不管是升序还是降序。此时快速排序最慢,一般当数据量很大的时候,用快速排序比较好,为了避免原来的序列有序。

场景题:如果我有100G文件,但是只有 500 M 的内存,这些文件存着一行行的数字,如何获取最小的10个?

这是经典的 Top K 问题,分治+堆排,我们可以先进行一个将文件进行分治,将100G的文件的分成一个个的 500 M,以此放到内存中每个500M的文件取出进行最小堆的排序,取出前10个写到新文件中。再对着一个个的新文件进行合并成 500 M 再进行最小堆的排序,最终获取最小的10个数字。

算法:最长有序括号,常见题,秒

更多内容可关注 微信公众号/B站:小生凡一

参考链接