滴滴前端笔试总结

298 阅读7分钟

🎉 面试前复习总结知识点

🎇平常题

1.SQL查询中用到的关键词主要包含6个

  • SQL的语法顺序:SELECT -> FROM ->WHERE->GROUP BY-> HAVING-> UNION-> ORDER BY
  • SQL的执行顺序:FROM -> WHERE ->GROUPBY ->HAVING ->SELECT ->UNION ->ORDER BY
  • 查询条件中出现联合索引第一列,或者全部,则能利用联合索引。查询条件中没有出现联合索引的第一列,而出现联合索引的第二列,或者第三列,都不会利用联合索引查询。

2.浏览器中可以使用LRU(least recently used)内存淘汰旧数据的策略,如果内存需要加载新数据但又空间不足,则会按照最近访问时间进行排序,并将最老的数据淘汰,假设现在内存空间大小为6,原本内存中没有数据,对内存中的数据的访问顺序如下:1,2,5,3,4,6,1,4,3,6,7,8,3,9,则缺页次数为(10)

image.png

3.以下哪个指令对象不可以用来做对象(obj)文件的分析:objdump, nm,ar

  • 脏读:一个事务读到另一个事务,尚未提交的修改,就是脏读。
  • 不可重复读:在同一个事务中,再次读取数据时(select操作),所读取的数据,和第1次读取的数据,不一样了。就是不可重复读。
  • 幻读:事务1读取指定的where子句所返回的一些行。然后,事务2插入一个新行,这个新行也满足事务1使用的查询where子句。然后事务1再次使用相同的查询读取行,但是现在它看到了事务2刚插入的行。

5.UDP最大包长度:65535

6.网页从打开到显示,经历了哪些过程

  • 在客户端浏览器中输入网址URL。
  • 发送到DNS(域名服务器)获得域名对应的WEB服务器的IP地址。
  • (客户端浏览器)与WEB服务器建立TCP(传输控制协议)连接。
  • (客户端)浏览器向对应IP地址的WEB服务器发送相应的HTTP或HTTPS请求。
  • WEB服务器响应请求,返回指定的URL数据或错误信息;如果设定重定向,则重定向到新的URL地址。
  • (客户端)浏览器下载数据,解析HTML源文件,解析的过程中实现对页面的排版,解析完成后,在浏览器中显示基础的页面。
  • 分析页面中的超链接,显示在当前页面,重复以上过程直至没有超链接需要发送,完成页面的全部显示。

7.HTML5新增的input的type类型

  • color ——拾色器
  • date ——日期
  • datetime ——日期(UTC时间)
  • datetime-local ——带时间的日期(无时区)
  • email ——电子邮件地址
  • month ——月份
  • number ——数值
  • range ——滑块控件(区域)
  • search ——搜索领域
  • tel ——电话号码
  • time ——时间 24小时格式
  • url ——URL地址(网站)
  • week ——选择周和年

8.hover :hover CSS伪类适用于用户使用指示设备虚指一个元素(没有激活它)的情况。 这个样式会被任何与链接相关的伪类重写,像:link, :visited, 和 :active等。 为了确保生效,:hover规则需要放在:link和:visited规则之后,但是在:active规则之前,按照 LVHA 的循顺序声明 :link-:visited-:hover-:active。 :hover伪类可以任何伪元素上使用。 【注意】: 在触摸屏上 :hover 有问题,基本不可用。不同的浏览器上:hover 伪类表现不同 【使用】:hover 伪类可以创建复杂的层叠机制。比如,创建一个纯CSS的下拉按钮(不使用JavaScript)。 :hover 伪类可以让你实现一个当鼠标悬停在图片上时全图预览的画廊功能。

9.mouseover 当鼠标指针位于元素上方时,会发生 mouseover 事件。 该事件大多数时候会与 mouseout 事件一起使用。 【补充】 mouseover支持[事件冒泡],mouseenter不支持事件冒泡。

  • ① 只要鼠标指针移入(或移出)事件所绑定的元素或其子元素,都会触发mouseover(或mouseout)事件
  • ② 只有鼠标指针移入(或移出)事件所绑定的元素时,才会触发mouseenter(或mouseleave)事件

10.所谓死锁,指的是两个或两个以上的进程在执行过程中,由于竞争资源或者由于彼此通信而造成的一种阻塞的现象,如果无外力作用,那么它们都将无法推进下去。此时,称系统 处于死锁状态或系统产生了死锁,这些永远在互相等待的进程称为死锁进程。
产生死锁的四个必要条件:

  • 互斥(资源独占):一个资源只能由一个进程使用
  • 请求与保持(部分分配,占有申请)
  • 不可剥夺(不可抢占)
  • 循环等待
    【注】只要上述条件之一不满足,就不会发生死锁。
    预防死锁:
  • 破坏部分分配条件
  • 破坏不可剥夺条件
  • 破坏循环等待条件

避免死锁的方法: —银行家算法 【基本思想】:检查申请者对各类资源的最大需求量,如果系统现存的各类资源可以满足它的最大需求量时,就满足当前的申请。

11.js 中math 向下取整

parseInt(5.1234); // 5 只保留整数部分(丢弃小数部分)
Math.floor(5.1234); // 5 向下取整(<= 该数值的最大整数,和parseInt()一样)
Math.ceil(5.1234); // 6 向上取整(有小数,整数部分就+1)
Math.round(5.1234); // 5 四舍五入(小数部分)
Math.round(5.6789); // 6
Math.abs(-1); // 1 取绝对值
Math.max(1,2); // 2 返回两数中的较大者
Math.min(1,2); // 1 返回两数中的较小者
Math.random(); // 随机数(0-1)
  1. socket套接字 sock_stream 流式socket 针对什么协议
  • 常用的Socket类型有两种:
  • 流式Socket(SOCK_STREAM)和数据报式Socket(SOCK_DGRAM)。
  • 流式是一种面向连接的Socket,针对于面向连接的TCP服务应用;
  • 数据报式Socket是一种无连接的Socket,对应于无连接的UDP服务应用。

🎇编程题

  • 1.给定无序整数序列,求连续子串最大和。遍历依次,求从第一个数开始累加的和,并记录最大值和最小值,最小值和最大值的差就是子序列最大的和。
/**
 * @param {number[]} nums
 * @return {number}
 */
var maxSubArray = function(nums) {
        let pre = 0, maxAns = nums[0]
        nums.forEach((x)=>{
            pre = Math.max(pre + x, x)
            maxAns = Math.max(maxAns, pre)
        })
        return maxAns
};
//ACM写法 JavaScript(V8)
/**
 * @param {number[]} nums
 * @return {number}
 */
(function() {
    //从控制台的到的是一个数组字符串。要进行处理
    let nums = readline().replace('[', '').replace(']', '').trim().split(',');
    let maxSubArray = function(nums) {
        let pre = 0,
            maxAns = nums[0]
        nums.forEach((x) => {
            pre = Math.max(pre + x, x)
            maxAns = Math.max(maxAns, pre)
        })
        return maxAns
    };
    maxSubArray()
    print(maxAns)
})()
//ACM写法 JavaScript(Node)
/**
 * @param {number[]} nums
 * @return {number}
 */
 
const readline = require('readline')
const rl = readline.createInterface({
    input: process.stdin,
    output: process.stdout
})
rl.on('line', function(line) {
    let nums = line.replace('[', '').replace[']', ''].trim().split(',')
    let maxSubArray = function() {
        let pre = 0
        let maxAns = nums[0];
        nums.forEach((x) => {
            pre = Math.max(pre + x, x)
            maxAns = Math.max(maxAns, pre)
        })
        return maxAns
    };
    console.log(maxSubArray())
    process.exit(0)
})
 
  • 2.给定无序整数序列,求其中第K大的数。思路:采用两个指针left和right,分别从数组起始和末尾开始查找,满足left左侧的元素小于等于current值,right右侧的元素大于等于current,直至left = right。返回left指针位置,根据left和K的关系,确定下一步的查找范围。直接上ACM的写法。如果大家想了解ACM使用JavaScript(V8)或者JavaScript(Node)的写法可以来这个连接观看:juejin.cn/editor/draf…
/**
 * @param {number []} nums
 * @param {number} k
 * @return {number} 
 **/
const readline = require('readline')
const rl = readline.createInterface({
    input: process.stdin,
    output: process.stdout
})
let rows = []
rl.on('line', function(line) {
    rows.push(line.trim())
        //获取输入的值,是字符串,要进行处理
    let k = rows[1],
        nums = rows[0].replace('[', '').replace(']', '').trim().split(',').map(Number)
        //核心的逻辑算法
    let findKthLargest = function() {
            const minHeap = new MinHeap()
            for (const num of nums) {
                minHeap.insert(num)
                if (minHeap.size() > k) {
                    minHeap.extract()
                }
                return minHeap.findMinimum()
            }
        }
        //创建最小堆的类
    class MinHeap {
        constructor() {
                this.heap = []
            }
            //用于比较新旧节点的值
        Equal(a, b) {
                if (a < b) return true
            }
            //得到根节点的节点
        getLeftIndex(index) {
                return 2 * index + 1
            }
            //得到根节点的右节点
        getRightIndex(index) {
                return 2 * index + 2
            }
            //得到父节点
        getParentIndex(index) {
                return Math.floor((index - 1) / 2)
            }
            //插入节点
        insert(value) {
                if (!value) {
                    this.heap.push(value)
                    this.shiftUp(this.heap.length - 1)
                    return true
                }
                return false
            }
            //不断地向上移动
        shiftUp(index) {
            let parent = this.getParentIndex(index)
            while (index > 0 && this.Equal(this.heap[index], this.heap[parent])) {
                [this.heap[index], this.heap[parent]] = [this.heap[parent], this.heap[index]]
                index = parent
                parent = this.getParentIndex(index)
            }
        }
        size() {
            return this.heap.length
        }
        isEmpty() {
            return this.heap.length == 0
        }
        findMinimum() {
                return this.isEmpty() ? undefined : this.heap[0]
            }
            //移除元素
        extract() {
            if (this.isEmpty()) {
                return undefined
            }
            if (this.size() == 1) {
                return this.heap.shift()
            }
            const removeValue = this.heap.shift()
            this.shiftDown(0)
            return removeValue
        }
        shiftDown(index) {
            let element = index
            const left = this.getLeftIndex(index)
            const right = this.getRightIndex(index)
            const size = this.size()
            if (left < size && this.Equal(this.heap[element], this.heap[left])) {
                element = left
            }
            if (right < size && this.Equal(this.heap[element], this.heap[right])) {
                element = right
            }
            if (index != element) {
                [this.heap[index], this.heap[element]] = [this.heap[element], this.heap[index]]
                this.shiftDown(element)
            }
        }
    }
    console.log(findKthLargest())
    process.exit(0)
})

🎉 面试后归纳知识点

🎇平时题

1.PV操作 PV操作是由P操作原语和V操作原语组成(原语是不可能中断的过程),操作对象是信号量。具体的:
P(S):① 将信号量S的值减1,即S=S-1;② 如果S>=0,则该进程继续执行;否则进程进入等待队列,置为等待状态。
V(S):① 将信号量S的值加1,即S=S+1;② 如果S>0,则该进程继续执行;否则释放等待队列中第一个等待信号量的进程。(因为将信号量加1后仍然不大于0,则表示等待队列中有阻塞的进程。)

使用PV操作和信号量可以实现进程间的同步和互斥。

  1. HTML5新特性-结构标签
    1. <article>标签:定义独立的内容。

    2. <aside>标签:定义所处内容之外的内容。常用于做文章的侧边栏。

    3. <figure>标签:定义独立的流内容(图像、图表、照片、代码等等)。常用来做一组媒体对象及其文字描述的容器。

    4. <figcaption>标签:定义文档中插图的图像,带有一个标题,与<figure>结合使用,用作figure的标题:

    5. <header>标签:定义页眉内容。

    6. <footer>标签:定义页脚。

    7. <nav>标签:定义导航栏。

    8. <section>标签:定义文档中的区段。

    • 新block标签:header,footer,main,aside,article,section,nav,hgroup (主要8个)。
    • 新表单标签,calendar、date、time、email、url、search
    • 媒介标签: video 和 audio
    • 绘画标签: canvas
  2. SQL中的锁

image.png

用DFS遍历一个无环有向图,并在DFS算法退栈返回时打印相应的顶点,则输出的顶点序列是:逆拓扑有序。