前端开发知识学习打卡

525 阅读30分钟

2020-06-14

1. 页面导入样式时,使用link和@import有什么区别?

  1. link是HTML标签,@import是css提供的。
  2. link引入的样式页面加载时同时加载,@import引入的样式需等页面加载完成后再加载。
  3. link没有兼容性问题,@import不兼容ie5以下。
  4. link可以通过js操作DOM动态引入样式表改变样式,而@import不可以。
  5. link除了能够加载CSS外,还能够加载RSS等其他事物,但是@import只能加载CSS。

2. 圣杯布局和双飞翼布局的理解和区别,并用代码实现

两种布局的主要作用:

圣杯布局和双飞翼布局解决的问题是一样的,就是两边顶宽,中间自适应的三栏布局,中间栏要在放在文档流前面以优先渲染。

两种布局的区别:

圣杯布局:为了中间div内容不被遮挡,将中间div设置了左右padding-left和padding-right后,将左右两个div用相对布局position: relative并分别配合right和left属性,以便左右两栏div移动后不遮挡中间div。

双飞翼布局:为了中间div内容不被遮挡,直接在中间div内部创建子div用于放置内容,在该子div里用margin-left和margin-right为左右两栏div留出位置。

代码实现:

<!-- 圣杯布局 -->

<div class="content">
    <div class="center">center</div>
    <div class="left">left</div>
    <div class="right">right</div>
</div>

<style>
    * {
        margin: 0;
        padding: 0;
    }

    .content {
        height: 500px;
        background: #ccc;
        padding: 0 200px 0 180px;
        box-sizing: border-box;
    }

    .content .center {
        width: 100%;
        height: 100%;
        background: lightblue;
        float: left;
    }

    .content .left {
        width: 180px;
        height: 100%;
        background: lightcoral;
        float: left;
        margin-left: -100%;
        position: relative;
        left: -180px;
    }

    .content .right {
        float: left;
        width: 200px;
        height: 100%;
        background: orange;
        margin-left: -200px;
        position: relative;
        right: -200px;
    }
</style>
<!-- 双飞翼布局 -->
<div class="content">
    <div class="center">
        <div class="center-content">center</div>
    </div>
    <div class="left">left</div>
    <div class="right">right</div>
</div>

<style>
    * {
        margin: 0;
        padding: 0;
    }

    .content {
        height: 500px;
        background: #ccc;
        box-sizing: border-box;
    }

    .center {
        float: left;
        width: 100%;
        height: 100%;
        background: lightblue;
    }

    .center-content {
        height: 100%;
        background: lightskyblue;
        margin: 0 180px 0 200px;
    }

    .left {
        float: left;
        width: 200px;
        height: 100%;
        background: lightcoral;
        margin-left: -100%;
    }

    .right {
        float: right;
        width: 180px;
        height: 100%;
        background: orange;
        margin-left: -180px;
    }
</style>

3. 用递归算法实现,数组长度为5且元素的随机数在2-32间不重复的值

这是一道大题目,把考点拆成了4个小项;需要侯选人用递归算法实现(限制15行代码以内实现;限制时间10分钟内完成)

  1. 生成一个长度为5的空数组arr
  2. 生成一个(2-32)之间的随机整数rand
  3. 把随机数rand插入到数组arr内,如果数组arr内已存在与rand相同的数字,则重新生成随机数rand并插入到arr内[需要使用递归实现,不能使用for/while等循环]
  4. 最终输出一个长度为5,且内容不重复的数组arr。
function randomNum(start, end) {
    let temp = Math.random() * (end - start) + start + 1;
    return Math.floor(temp);
}
let resultArray = [];
function randomArray() {
    if (resultArray.length >= 5) return 0;
    let tempNum = randomNum(2, 32);
    if (!resultArray.includes(tempNum)) {
        resultArray.push(tempNum);
    }
    randomArray();
}
randomArray();

console.log(resultArray);

2020-06-15

1. html的元素有哪些(包含H5)

我认为可以从多个方面进行归类总结,这里列出我自己的归类角度:

最常用的标签: div h1-h6 p img button input select option textarea span iframe em

HTML文件头部的标签: html head title meta script link style

列表相关标签: ul li ol oi

表格相关标签: table thead tbody tfoot tr th td

换行和分割线标签: br hr

H5新增标签: header footer section article audio video

2. CSS3有哪些新增的特性

边框: border-radius box-shadow border-image

背景: background-size background-origin background-clip

渐变: linear-gradient radial-gradient

文本效果: word-wrap work-break text-overflow text-shadown text-outline text-justify

转换: transform(包含2D和3D)

**过渡:**transition

动画:@keyframes animation

弹性盒模型: flex justify-content align-item等

媒体查询: @media

3. 写一个方法去掉字符串中的空格

要求传入不同的类型分别能去掉前、后、前后、中间、所有的空格

function trimStr(_str, trimType) {
  switch(trimType) {
    case "left":
      return _str.replace(/^\s*/, "")
    case "right":
      return _str.replace(/\s*$/, "")
    case "center":
      return _str.replace(/(\S*)(\s*)(\S*)/g, `$1$3`)
    case "both":
      return _str.replace(/^\s*/, "").replace(/\s*$/, "")
    case "all":
      return _str.replace(/\s/g, "")
  }
}

2020-06-16

1. HTML5的文件离线存储怎么使用,工作原理是什么

如何使用HTML5的文件离线存储

  1. 创建cache manifest文件,告知浏览器应该将哪些文件离线存储。

cache manifest 文件相当于一份解析清单,浏览器通过解析这个清单,能够很明确的知道应该离线哪些文件,该清单可分为三部分。如下所示,下面的配置我们可以命名为“demo.appcache”

# 第一部分,列出需要离线储存的文件
# 比如这里列出了两个文件,当用户访问网站的时候,浏览器会将这连个文件离线存储到本地
# 然后,即使用户和网络断开或者改网站关闭,这两个资源依然可以使用
CACHE MANIFEST
/image/dog.jpg
/theme.css

# 第二部分,配置不需要离线缓存的白名单
# 这里可以使用通配符"*", 告诉浏览器,所有不在第一部分出现的文件,都默认使用HTTP相关缓存头策略
# 这里也可以指定某些具体的文件,表明这些文件需要使用HTTP相关缓存头策略
NETWORK
*
login.js   


# 第三部分,设置一个页面,如果网站中的页面不能访问的时候,跳转到这个页面
FALLBACK
/404.html

  1. 在html文件中,使用定义好的cache manifest文件
<!DOCTYPE html> 
<html lang="en" manifest="demo.appcache"> 
    <head> 
        <meta charset="UTF-8"> 
        <title>HTML5离线存储</title>
    </head> 
    <body> 
        <img src="image/01.jpg" alt=""> 
        <img src="image/02.jpg" alt=""> 
    </body> 
</html>

HTML5文件离线存储的原理

浏览器通过解析cache manifest文件,会知道哪些文件需要被离线存储,然后这些文件资源会想cookie一样被存储下来,在之后访问网站的过程中,如果需要这些文件资源,浏览器将直接从本地离线文件中进行读取。即使用户处于离线模式或者网站关闭的情况下,这些离线文件依旧可以被访问。

这里只是简单介绍了HTML5文件离线存储,具体细节可以参考一下两篇文章:

  1. HTML5离线存储原理
  2. HTML5存储方式

2. CSS选择器有哪些?哪些属性可以继承?

www.h-camel.com/show/11.htm…

CSS中的选择器:

标签选择器:div p table span

类选择器:.red .active

ID选择器: #demo #title

伪类选择器:.test::after

属性选择器:[type='input']

后代选择器:div > span

兄弟选择器: div + span

通配符选择器:*

CSS中可以继承的属性:

字体系列属性:

属性简介
font-family规定元素的字体系列
font-weight设置字体的粗细
font-size设置字体的尺寸
font-style定义字体的风格
font-variant设置小型大写字母的字体显示文本,这意味着所有的小写字母均会被转换为
文本系列属性:
属性简介
text-indent文本缩进
text-align本水平对齐
line-height行高
word-spacing增加或减少单词间的空白(即字间隔)
letter-spacing增加或减少字符间的空白(字符间距)
text-transform控制文本大小写
direction规定文本的书写方向
color文本颜色

此外还有:

属性简介
元素可见性visibility
表格布局属性caption-side、border-collapse、border-spacing、empty-cells、table-layout
列表属性list-style-type、list-style-image、list-style-position、list-style
生成内容属性quotes
光标属性cursor
页面样式属性page、page-break-inside、windows、orphans
声音样式属性speak、speak-punctuation、speak-numeral、speak-header、speech-rate、volume、voice-family、pitch、pitch-range、stress、richness、、azimuth、elevation

3. 写一个方法把下划线命名转成大驼峰命名

function replaceName(_str) {
  return _str.replace(/(\w)(_)(\w)/g, (match, $1, $2, $3) => `${$1}${$3.toUpperCase()}`)
}

2020-06-17

1. 简述超链接target属性的取值和作用

超链接的target属性有四种取值,他们的作用分别是:

取值描述
_blank在新窗口打开被链接文档
_self默认值。在相同框架中打开被链接文档
_parent在父框架集中打开被链接文档
_top在整个窗口中打开被链接文档
framename在指定的框架中打开被链接文档

2. CSS3新增伪类有哪些并简要描述

CSS3中新增伪类很多,这里列出常用的几类,具体信息可以参考:MDN-CSS

名称描述
:first-child :last-child第一个和最后一个元素,表示子元素结构关系
:first-of-type :last-of-type属于其父元素的第一个或最后一个指定类型的元素
:nth-child() :nth-last-child()传入数字、2n或2n+1,选中某一个、偶数行、奇数行的元素
:nth-of-type() :nth-last-of-type()传入数字、2n或2n+1,选中指定类型的某一个、偶数行、奇数行的元素
:not()传入标签,传入不是这个标签的元素
:enabled :disabled选中启动和被禁用的元素
:checked选中状态的radio、checkbox或select选中的option
:root文档根元素,总是返回html
:default一组相关元素中的默认表单元素

3. 写一个把字符串大小写切换的方法

非正则表达式写法

function changeLowerAndUpper(_str) {
  let newCharArray = [];
  if (_str && _str.length > 0) {
    for (let char of _str) {
      if (char.charCodeAt() >= 97 && char.charCodeAt() <= 122) {
        char = String.fromCharCode(char.charCodeAt() - 32);
      } else if(char.charCodeAt() >= 65 && char.charCodeAt() <= 90) {
        char = String.fromCharCode(char.charCodeAt() + 32);
      }
      newCharArray.push(char);
    }
  }
  return newCharArray.join("");
}

console.log(changeLowerAndUpper("AllenFeng"));

正则表达式写法

function changeLowerAndUpper(_str) {
    return _str.replace(/([a-z]*)([A-Z]*)/g, (match, $1, $2) => `${$1.toUpperCase()}${$2.toLowerCase()}`);
}
console.log(changeLowerAndUpper("AllenFeng"));

2020-06-18

1. label都有哪些作用?并举相应的例子说明

关联一个表单控件(比如:checkbox、radio),通过点击label标签,达到点击控件的目的
<!-- 单击关联标签激活input,需给input一个id属性,给label一个for属性,设为同一个值 -->

<label for="my-check-box">My Check Box</label>
<input type="checkbox" id="my-check-box" >

<label for="my-radio">My Radio</label>
<input type="radio" id="my-radio" >
利用label来模拟button,解决不同浏览器原生button样式不一致的问题
<input type="button" id="btn">
<label for="btn">Button</label>

<style>
    input[type='button'] {
        display: none;
    }

    label {
        display: inline-block;
        padding: 10px 20px;
        background: #456;
        color: #fff;
        cursor: pointer;
        box-shadow: 2px 2px 4px 0 rgba(0,0,0,.3);
        border-radius: 2px;
    }
</style>

2. 用css创建一个三角形,并简述原理

示例代码:

<div class='rect'></div>
<style>
    .rect {
        width: 0;
        height: 0;
        background-color: #fff;
        border-right: 100px solid rgb(34, 230, 220);
        border-left: 100px solid rgb(202, 146, 25);
        border-top: 100px solid rgb(29, 156, 194);
        border-bottom: 100px solid rgb(16, 204, 101);
    }
</style>

原理简述:

将一个元素的宽高设置为0,然后分别为上右下左四个边框设置border-width、border-style、border-color。通过将不同的边框的border-color设置为transparent,即可得到不同的三角形

3. 写一个去除制表符和换行符的方法

function replaceStr(_str) {
    if (typeof _str !== "string") {
        return _str;
    }
    return _str.replace(/[\t\n]/gu, "");
}

2020-06-22

1. iframe框架都有哪些优缺点

优点:

  1. 对于多页面应用来讲,可以增强代码的复用性。比如对相同的header、footer,可以通过iframe引用
  2. 可以实现异步刷新,单个iframe的刷新不会影响整体窗口的刷新
  3. 可以实现跨域,每个iframe的源都可以不相同,方便引入第三方内容

缺点:

  1. 代码复杂,无法被一些搜索引擎爬取到,不利于SEO
  2. 会产生很多页面,不利于管理
  3. 多个iframe可能都会产生水平和垂直方向的滚动条,影响页面的UI效果,用户体验不好。
  4. iframe框架页面会增加服务器的http请求,对于大型网站是不可取的

2. 简述你对BFC规范的理解

BFC(Block Formatting Context)即块级格式化上下文,是一种CSS排版规范。BFC具有以下特性:

  1. 如果一个 DOM 元素具有 BFC,那么它内部的子元素不会影响外面的元素;外面的元素也不会影响到其内部元素。
  2. 计算BFC的高度是,浮动元素也会参与计算。即浮动元素可以单独撑起父元素的高度。
  3. BFC的区域不会与float的元素区域重叠。

对于一个块级元素来说,想要符合BFC模型,至少要满足以下条件中的一个:

  1. 定位条件:position为absolute或者fixed
  2. overflow条件:overflow为auto、hidden、scroll
  3. 浮动条件:float为left或者是right,元素浮动起来
  4. display条件:display是flex、inline-flex、inline-block、table-cell、table-caption
  5. html根元素

3. 统计某一字符或字符串在另一个字符串中出现的次数

function strShowCount(sourceStr, targetStr) {
  let reg = RegExp(targetStr, "g");
  let timer = 0;
  while(reg.exec(sourceStr)) {
    timer++;
  }
  return timer;
}

console.log(strShowCount("AllenFengeeeeeeFengALlenFen", "Feng"));

2020-06-28

1. 清除浮动的方式有哪些及优缺点

  • 通过给父元素添加些属性,触发父元素的BFC规则。BFC规则中有一条规定:浮动子元素也会参与高度的计算

  • 给父元素添加伪类,在伪类中清除浮动来达到这种效果。推荐这种写法,产生的DOM元素少,副作用比较小。

    .parent::after {
        content: "";
        display: block;
        clear: both;
    }
    
  • 在父元素中额外添加一个元素,在这个新增元素中清除浮动。类似上述伪类的做法

  • 直接设置父元素的高度。但是非常不推荐这种做法。

2. 浏览器内多个标签页之间的通信方式有哪些

如果多个标签页之间不涉及跨域,那么可以使用cookie或localStorage方式来进行通信。

如果涉及到跨域问题,那么可以采用WebSocket或postMessage来进行通信。

3. 简述下你理解的优雅降级和渐进增强

渐进增强和优雅降级这两个概念是在 CSS3 出现之后火起来的。由于低级浏览器不支持 CSS3,但是 CSS3 特效太优秀不忍放弃,所以在高级浏览器中使用 CSS3,而在低级浏览器只保证最基本的功能。

**优雅降级: **先不考虑兼容,优先最新版本浏览器效果,之后再逐渐兼容低版本浏览器。

**渐进增强:**考虑兼容,以较低(多)浏览器效果为主,之后再逐渐增加对新版本浏览器的支持,以内容为主

4. 写一个判断数据类型的方法

function type (obj) {
    return Object.prototype.toString.call(obj).replace(/\[object\s|\]/g,'');
}

console.log(type([]))  //"Array"
console.log(type(1))  //"Number"

2020-06-30

1. viewport常见设置都有哪些

在移动端做开发时,必须要搞清楚 viewport 这一设置。

viewport 就是视区窗口,也就是浏览器中显示网页的部分。PC 端上基本等于设备显示区域,但在移动端上 viewport 会超出设备的显示区域(即会有横向滚动条出现)。 设备默认的 viewport 在 980 - 1024 之间。

为了让移动端可以很好地显示页面,因此需要对 viewport 进行设置。相关的设置值如下

设置解释
width设置 layout viewport 的宽度,为一个正整数,或字符串"width-device"
initial-scale设置页面的初始缩放值,为一个数字,可以带小数
minimum-scale允许用户的最小缩放值,为一个数字,可以带小数
maximum-scale允许用户的最大缩放值,为一个数字,可以带小数
height设置 layout viewport 的高度,这个属性对我们并不重要,很少使用
user-scalable是否允许用户进行缩放,值为"no"或"yes", no 代表不允许,yes 代表允许

viewport 是在 meta 标签内进行控制:

// width=device-width, initial-scale=1.0 是为了兼容不同浏览器
<meta
      name="viewport"
      content="width=device-width, initial-scale=1.0, maximum-scale=1.0, user-scalable=0"
      />

2. 对比下px、em、rem有什么不同

px: 绝对固定的值,无论页面放大或者缩小都不会改变。

em: 相对于自身元素的font-size属性,如果自身元素font-size: 25px,并且width: 2em,那么该元素最终的实际宽度为50px(25 * 2 = 50)

rem: 和em类似,只不过是相对于根元素(即html元素)的font-size属性

3. 简要描述下什么是回调函数并写一个例子出来

比如目前有两个函数A和B,将B作为参数传给函数A,在A函数中,一开始不去执行函数B,只有当满足一定条件的时候,再来执行函数B。此时函数B就是一个回调函数。实例如下:

function A(num, fun) {
    console.log("我是函数A");
    console.log("我用来处理一个数字");
    console.log("我接受的数字是: ", num);
    if (num  > 10) {
        console.log("我接受的数字大于10,开始执行回调函数B");
        fun();
    }
}

function B(){
    console.log("我是回调函数B");
}

A(5, B);
A(12, B);

2020-07-01

1. 你对标签语义化的理解是什么

标签语义化的概念:让正确的标签做正确的事情,比如对于一个大的盒子,可以使用div,对于一个段落,可以使用p标签,对于一行文字中的一部分文字,可以使用span标签。对于标题使用h1-h6等等。

标签语义化的优点:有利于SEO、方便代码的维护和迭代、有利于浏览器识别。

2. CSS常用的布局方式有哪些

圣杯布局、双飞翼布局、flex布局

详情内容可以参考文章:CSS 常见布局方式

3. 简要描述下JS有哪些内置的对象

JS 的内置对象也称为“全局作用域里的对象”。与“全局对象”不同,全局对象是通过 this 访问(在浏览器里也就是 window 对象)。详情可以参考文档: JavaScript 标准内置对象

对象名称JS对象
时间对象Date
字符串对象String
数学对象Math
数值对象Number
数组对象Array
函数对象Function
函数参数集合arguments
布尔对象Boolean
错误对象Error
基础对象Object

2020-07-04

1. 常见的浏览器内核都有哪些?并介绍下你对内核的理解

浏览器浏览器内核
IETrident 内核
ChromeWebkit 内核
火狐Gecko 内核
欧朋Presto
SafariWebkit 内核

浏览器内核即:浏览器的核心部分。按功能划分可以分为渲染引擎和JS引擎,前者用于渲染页面,后者用于解析JavaScript。但是由于Js引擎越来独立,所以我们谈起的浏览器内核多为渲染引擎。

2. 说说你对css盒子模型的理解

  1. css盒模型由两个盒子组成,外在的控制是否换行的盒子,以及内在的控制元素内容的盒子。比如:display: inline-block, 则它的外在的盒子就是inline也就是不占据一行,而block则表示内部的元素具有块状特性。所以,display: inline其实就是display: inline-inline的缩写,display: block就是display: block-block的缩写。
  2. 每一个内在的盒子有: width/height, padding, border, margin这几个控制盒子大小的属性。其中 width/height控制元素内容大小,padding则控制元素内容到border线内侧距离,border则是元素外围边框大小,而margin则是控制与其他元素的间距,它的背景透明。
  3. 对于早期,计算一个元素的占据大小,需要通过width +2* padding + 2*border来计算,css3中提出了box-sizing:border-box,通过这样设置,就可以使元素最终的宽高就是设定的width/height, 浏览器会根据width/height, padding, border的大小来自动调整内部元素的大小。

3. 写一个获取当前url查询字符串中的参数的方法

function getParamsFromUrl(url) {
    if (!url || url.indexOf("?") === -1) {
        return {};
    }

    let parmasStr = url.slice(url.indexOf("?") + 1);
    let paramObj = {};
    let key = "";
    let value = "";

    parmasStr.split("&").forEach(str => {
        key = str.slice(0, str.indexOf("="));
        value = str.slice(str.indexOf("=") + 1);
        if (key) {
            paramObj[key] = value;
        }
    });
    return paramObj;
}

console.log(getParamsFromUrl(window.location.href));

// 大佬的写法

function urlParam(){
    const param = {};
    location.search.replace(/([^&=?]+)=([^&]+)/g,(m,$1,$2)=> param[$1] = $2);
    return param;
}

2020-07-05

1. html5中的form怎么关闭自动补全

解释: 在部分浏览器上,foucs输入框可以把之前输入过的值自动填入,如果不想自动填入,可以关掉它; autocomplete="off" 默认是"on" 开启状态

一般业务下不会调整这个自动完成,因为对产品来说简化用户操作,建议打开。

2. ::before和:after中单冒号和双冒号的区别是什么,这两个伪元素有什么作用

  1. :表示伪类,是一种样式,比如:hover, :active等
  2. ::表示伪元素,是具体的内容,比如::before是在元素前面插入内容,::after则是在元素后面插入内容,不过需要content配合,并且插入的内容是inline的。
  3. :before和:after其实还是表示伪元素,在css3中已经修订为::before和::after了,只是为了能兼容IE浏览器,所以也可以表示成:before和:after

推荐阅读博客: 属性content有什么作用呢?有哪些场景可以用到?

3. 说说你对javascript的作用域的理解

  1. 全局作用域:这个没啥说的,就是在顶层环境中申明的变量都是全局作用域,他们的属性其实都在window对象下面。
  2. 函数作用域:在函数内部定义的变量都是函数作用域,只能在函数中访问到,当然也可以通过闭包来访问。除此之外,在其他地方是没法访问函数内部的变量的。
  3. 局部作用域:es6中新增的特性,弥补了以前只能使用匿名及时运行函数来创建局部变量的缺陷。使用很简单,直接用let来申明变量就行。也可以使用const来申明变量,表明这是常数。

2020-07-06

1. 为什么HTML5只需要写 <!DOCTYPE HTML> 就可以

DOCTYPE是document type的缩写,在HTML中用来区分标准模式和怪异模式的声明,用来告知浏览器用标准模式渲染页面,此声明需要位于文本的第一行。

因为 HTML5 与 HTML4 基于的基准不同。HTML4 基于 SGML 因此需要除了 DOCTYPE 外还需要引入 DTD 来告诉浏览器用什么标准进行渲染。DTD 还分为标准模式、严格模式。如果什么都不写,就完全让浏览器自我发挥,会变成怪异模式。

HTML5 不基于 SGML,因此后面就不要跟 DTD,但是需要 DOCTYPE 来规范浏览器的渲染行为。

注:SGML 是通用标记语言的集合。其中有 HTML、XML,因此需要用 DTD 来指定使用那种规范

2. position:fixed;在ios下无效该怎么办

当采用 fixed 做吸底、吸顶布局时,如果触发键盘弹出事件则 fixed 属性会失效,布局就会被扰乱。其原因解释如下:

软键盘唤起后,页面的 fixed 元素将失效(即无法浮动,也可以理解为变成了 absolute 定位),所以当页面超过一屏且滚动时,失效的 fixed 元素就会跟随滚动了。

第三方库 isScroll.js 可以解决此问题。

解决的思路就是避免最外层出现滚动,即最外层使用 fixed 并且不让其可以滚动。让滚动仅在内部内容部分。

参考文章: Web 移动端 Fixed 布局的解决方案

3. 什么是闭包?优缺点分别是什么?

**定义:**在函数A中额外定义一个函数B,那么函数B可以访问函数A这个作用于中的变量,这是我们可以把函数B称作是一个闭包。广义上来讲:所有函数都是闭包,因为我们可以把全局作用于理解成一个很大的函数作用域,所有的函数都在这个函数作用域中,可以引用这个函数作用域的变量。

优点:

  1. 闭包可以达到隐藏变量的目的
  2. 防止变量被篡改
  3. 防止作用域的污染

比如如下实例:

function a(){
    var b = 1;
    var c = 2;
    // 这个函数就是个闭包,可以访问外层 a 函数的变量,将这两个变量隐藏
    // 同时防止这两个变量被篡改已经防止其他作用域的污染
    return function(){
        var d = 3;
        return b + c + d;
    }
}

var e = a();
console.log(e());

缺点:

闭包可能会引用上层局部作用域中的变量,使得这些变量不能及时地被回收,导致内存被消耗,甚至会有内存泄露的问题。

推荐阅读文章:关于闭包

2020-07-11

1. 元素的alt和title有什么区别?

alt属性常用于 img 标签,用作当图片不能正常显示的时候,代替图片显示在浏览器中的内容。非常推荐使用这个属性,即使图片无法正常加载,用户也可以通过alt属性中的信息,知道网页中丢失了什么数据。

title属性规定元素的额外信息,可用于很多标签,当用户将鼠标移至这些标签的时候,有一点工具提示文本帮助用户查看更多信息。

2. 请描述margin边界叠加是什么及解决方案

margin便捷叠加又叫做margin塌陷。在垂直方向上,如果两个div的margin分别是50px和100px,那么他们的上下间隔应该是150px,但是真是的间隔确实100px(两个margin中数值较大的那个)。这种现象就是margin边界叠加。

为什么要有margin塌陷,这看起来就是个bug,实际上翻看css的历史也不难理解,最开始的css就是为普通的文本和图像来服务的。一块块段落直接用上下margin来间隔,如果没有上下塌陷,那么第一个元素距离父元素顶部的距离要小于其他兄弟元素的上下间隔,因为他们的间隔可是下面兄弟元素margin-top +上面兄弟元素 margin-bottom了,视觉上就很怪,于是乎就设计成了塌陷。 这样的话,margin塌陷会让兄弟元素的间隔以及兄弟元素和父元素的间隔是一样的。

如果要解决这种现象,可以把margin边界叠加的元素放在不同的BFC盒子中,如果触发BFC:

  • 根元素 html
  • display 为flex、inline-block、table-cell、table-caption
  • overflow 的值不为visible
  • position的值为absolute或者fixed

3. 返回到顶部的方法有哪些?把其中一个方法出来

  1. 利用 a 标签的锚点。在顶部放一个 a 标签 顶部,在需要回到顶部的位置放置一个 a 标签,地址为 top[回到顶部](#top)。要做成隐藏的锚点,可以把内部的内容去掉,name 是必须的。
  2. 利用 #,在 url 后增加 # 不会让页面刷新,并且可以回到顶部。可以对 location.href 进行设置 location.href += '#'。当这个方法执行多次即有多个 # 时,页面不会有响应。
  3. 利用 javascript 设置 scrollTop = 0,一般设置在最外层,即 document.documentElement.scrollTop = 0 就可以返回顶部。

2020-07-13

1. 你认为table的作用和优缺点是什么呢

优点:

  • 样式简单且统一,能够减少div的使用
  • 兼容性好

缺点:

  • 需要写的内比较多,不利于维护
  • 容易导致回流,影响加载和渲染

2. 解释下 CSS sprites 的原理和优缺点分别是什么

原理: CSS sprites 即精灵图,它的原理是将多张图片整合到一张图片上,然后使用background-position + 固定宽高进行定位,显示不同的内容。

**优点: ** 能够减少http请求,减轻server端的压力

缺点:

  • 图片的位置计算比较复杂,有时计算失误还会导致图片显示错误。
  • 更新大图中的某一部分的时候,需要重新加载整张图片,缓存失效。

3. typeof('abc')和typeof 'abc'都是string, 那么typeof是操作符还是函数

typeof 是操作符,明确定义在MDN当中,作用是对后方表达式的返回做类型定义。 在后面添加括号其实是改变计算优先级,和四则运算中的括号可以等效理解。 简单举例:

typeof 123 //"number"
typeof 123+'abc'// "numberabc"
typeof(123+'abc') // "string"

2020-07-14

1. 怎样在页面上实现一个圆形的可点击区域

2. 什么是FOUC?你是如何避免FOUC的

FOUC 即 Flash of Unstyled Content,是指页面一开始以样式 A(或无样式)的渲染,突然变成样式B。这个过程中可能会出现白屏或者闪烁。原因是样式表晚于HTML加载导致页面进行重新绘制。

避免办法:通过link标签引入样式表,且把link标签放置于head中。

3. 你理解的"use strict";是什么? 使用它有什么优缺点

use strict 即启用严格模式,也就是对JS代码的要求更加严格。

**优点: **

  • 消除JS语法的一些不合理、不严谨之处,减少一些怪异行为
  • 消除代码运行的一些不安全之处,保证代码安全运行
  • 提高编译器的效率,增加运行速度
  • 为未来新版本的JS做好铺垫

常见的场景:

  • 禁止this关键字指向全局对象
  • 禁止在函数内部遍历调用栈
  • 全局变量必须显示声明
  • arguments不在跟踪函数的变化

2020-07-15

1. 说说你对html中的置换元素和非置换元素的理解

置换元素:这是很特殊的一类元素,通常他们有自己的尺寸,比如宽度、高度、宽高比等,CSS渲染不会对此类元素进行渲染,浏览器会根据他们的属性和标签,决定元素的具体显示内容。常见的置换元素有:img、input、textarea、select、object等。

非置换元素:除了置换元素之外的元素都是非置换元素,CSS在会对此类元素进行渲染,他们的内容会被浏览器渲染出来。常见的有:div、p、span等。

2. CSS的属性content有什么作用呢?有哪些场景可以用到?

content属性主要配合 ::before 和 ::after 两个伪元素使用,为其提供内容。项目中content经常用来设置icon

3. "attribute"和"property"有什么不同?

attribute 是HTML标签上的属性,它的值只能是字符串。通过JS设置attribute,新的属性会被添加到HTML元素上,比如:

<a class="demo" href="https://www.xunlei.com/" title="精彩,一下就有">精彩,一下就有</a>

那么我们可以在JS中通过以下方式读取a标签的attribute属性:

let a = document.getElementsByClassName("demo")[0];

console.log(a.getAttribute("title"));	// "精彩,一下就有"

a.setAttribute("name", "Allen Test");
console.log(a);		// <a class="demo" href="https://www.xunlei.com/" title="精彩,一下就有" name="Allen Test">精彩,一下就有</a>

需要注意的是,attribute是对大小写不敏感,比如:

// 下面语句全部会打印出:"精彩,一下就有"
console.log(a.getAttribute("title"));
console.log(a.getAttribute("TITLE"));
console.log(a.getAttribute("Title"))

// 设置attribute的时候,即使是属性包含大写字母,在实际的a标签上也会转换为小写
a.setAttribute("Test", "1")
console.log(a.getAttribute("test"));	// 1
console.log(a.getAttribute("Test"));	// 1
console.log(a);	// <a class="demo" href="https://www.xunlei.com/" title="精彩,一下就有" name="Allen Test" test="1">精彩,一下就有</a>

property 是DOM中的属性,即它是JS中的对象,他的值可以是字符串,也可以是对象。通过JS设置property,新的属性不会被添加到HTML元素上。而且,property对大小写敏感。比如:

let a = document.getElementsByClassName("demo")[0];

a.name = "Allen";
a.Name = "Upper Allen";
console.log(a.name);	// Allen
console.log(a.Name);	// Upper Allen
console.log(a);	// a标签不会有变化

2020-07-16

1. 请描述HTML元素的显示优先级

frame元素 > 表单元素 > 表单元素。

表单元素包括:文本输入框,密码输入框,单选框,复选框,文本输入域,列表框等等;

非表单元素包括:连接(a),div,table,span等。

所有的html元素又可以根据其显示分成两类:有窗口元素以及无窗口元素。有窗口元素总是显示在无窗口元素的前面。 有窗口元素包括:select元素,object元素,以及frames元素等等。 无窗口元素:大部分html元素都是无窗口元素。

2. 要让Chrome支持小于12px的文字怎么做

可以使用CSS3中的transform属性进行缩放,示例如下:

.text {
    font-size: 12px;
    transform: scale(0.5);
    -webkit-transform: scale(0.5);
}

3. Javascript身份证号码验证

算法较为复杂,建议参考博客:Javascript身份证号码验证

2020-07-17

1. 谈谈你对input元素中readonly和disabled属性的理解

相同点:都会使表单变成不可编辑状态

不同点:

  • readonly是只读(可能是某种特殊处理),disabled是禁用(可能是权限或其他原因),意义不同
  • disabled会使文本框变灰,readonly不会
  • disabled对所有表单都使用,readonly对hidden、radio、checkbox、range、color无效
  • disabled的值不会被form收集,readonly的值会

2. 说说你对line-height是如何理解的

line-height 行高,就是两行文字之间基线的距离,用来调整文字的行间距。

常用的单位有:px、em、rem、没有单位(没有单位的时候,表示font-size的倍数)。推荐使用不带单位的设置。

3. JS判断是否为中文的方法

// 匹配中文的正则:/[\u4e00-\u9fa5]/

function isAllChinese(str) {
    let reg = /^[\u4e00-\u9f5a]+$/;
    if (reg.test(str)) {
        return true;
    }
    return false;
}

function hasChinese(str) {
    let reg = /[\u4e00-\u9f5a]+/;
    if (reg.test(str)) {
        return true;
    }
    return false;
}

2020-07-19

1. js放在html的body和head中有什么区别?

在body中的js代码:

  • 会在页面加载的时候执行
  • 此处的代码经常用于生成页面的内容

在head中的js代码:

  • 此处多为需调用才会执行的脚本或者时间触发执行的脚本
  • 此处js代码的特点是在被调用的时候执行

2. 说说浏览器解析CSS选择器的过程

首先要注意方向问题,浏览器在解析CSS选择器的时候,是从右向左解析的。

比如对于以下CSS选择器:.box div p span。那么浏览器的解析顺序是:

  • 先找到标签是span的元素,这个元素我们标记为a
  • 查找a元素的祖先元素,如果a的祖先元素中有标签为p的元素,将该元素标记为b。否则a元素不是匹配CSS选择器的元素,此次解析CSS选择器结束。
  • 查找b元素的祖先元素,如果b的祖先元素中有标签为div的元素,将该元素标记为c。否则同上。
  • 查找c元素的祖先元素,如果c的祖先元素中有类名为box的元素,那么查找成功,之前的a元素,就是符合CSS选择器的元素,此次解析完成。否则同上。

为什么浏览器要进行逆向解析CSS选择器呢?是因为通过在众多HTML标签中,如果通过正向解析,每次都想从选择器中的祖先元素开始,经历若干次回溯才能确定,效率很低。

浏览器在解析完CSS选择器之后,会生成一个CSS Tree,和解析标签生成的HTML Tree结合,最终生成表示整个页面的对象,渲染到页面上。

针对以上之后,给出节点在写CSS选择器的一些建议:

  • 不要再id选择器前加其他的选择器。比如使用 #box 即可,无须使用 div#box.container #box
  • 使用class代替层级关系。比如使用 .box-a 代替 #box ul li a

3. 你对new操作符的理解是什么?手动实现一个new方法

new 操作符的作用:创建一个用户自定义的对象类型的实例,或创建一个具有构造函数的内置对象类型的实例。

比如,当执行 new Object() 代码的时候,new 操作符会做以下事情:

  • 创建一个新的对象,这里标记为a
  • 把新对象a的原型指向object构造函数中的prototype
  • 把object构造函数里的this指向新对象
  • 返回新对象a

手动实现代码如下:

// 首先定义一个构造函数,来使用new
function contructorTemp(name, height) {
    this.name = name;
    this.height = height;
}

contructorTemp.prototype.showName = function () {
    console.log("This name is: ", this.name);
}


function newFeng() {
    let tempObj = {};
    let Con = [].shift.call(arguments);
    tempObj.__proto__ = Con.prototype;
    let res = Con.apply(tempObj, arguments);
    return typeof res === "object" ? res : tempObj;
}

let a = newFeng(contructorTemp, "Allen, 175");

a.showName();

2020-07-22

1. 关于form标签的enctype属性你有哪些了解?

form标签的enctype属性指定将数据回发到服务器时,浏览器如何对表单数据进行编码,有三种编码形式:

说明
application/x-www-form-urlencoded默认。在发送前对所有字符进行编码(将空格转换为 "+" 符号,特殊字符转换为 ASCII HEX 值)。
multipart/form-data不对字符编码。当使用有文件(如图片、mp4等)上传控件的表单时,该值是必需的。
text/plain将空格转换为 "+" 符号,但不编码特殊字符。

具体信息可以参考文章:Form表单、四种常见的POST请求提交数据方式

2. 说说CSS的优先级是如何计算的

  • !important 的优先级最高,* {} 的优先级最低

  • ID选择器 > class选择器 > 标签选择器

  • 如果是组合选择器,可以将I-C-E公式记性计算优先级,其中I是id选择器,数值为100;C是class选择器,数值为10;E是标签选择器,数值为1;

    对于 #box .first div 的优先级数值是 100 + 10 + 1 = 111,#.first div p span 的优先级数值是 10 + 1 + 1 + 1 = 13。

    显然前一个的优先级比较高。

3. 0.1 + 0.2、0.1 + 0.3和0.1 * 0.2分别等于多少?并解释下为什么?

0.1 + 0.2 = 0.30000000000000004
0.1 + 0.3 = 0.4
0.1 * 0.2 = 0.020000000000000004

简单来说就是js中采用IEEE754的双精度标准,因为精度不足导致的问题,比如二进制表示0.1时这这样表示1001100110011...(0011无线循环),那么这些循环的数字被js裁剪后,就会出现精度丢失的问题,也就造成了0.1不再是 0.1 了,而是变成了 0.100000000000000002; 那么同样的,0.2 在二进制也是无限循环的,被裁剪后也失去了精度变成了 0.200000000000000002

2020-07-23

1. 说说你对属性data-的理解

这是HTML5新增的属性,我们可以使用该属性,在标签中额外存储一些信息,这些信息我们可以在JS和CSS中获取。需要额外注意的是,data-*属性中,必须使用小写字母,这是一种规范,同时也会影响到后面对数值的获取。

比如对于一个含有data-属性的标签:

<div class="data-ele" data-name="Allen" data-height="175" data-gender="male"></div>

在JS中我们可以通过以下方式获取到这些data-属性中的值:

let ele = document.getElementsByClassName("data-ele")[0];

// 可以通过getAttribute()获取标签的属性,相比于dataset,这种方式速度更快,兼容性更好
console.log(ele.getAttribute("data-name"));
console.log(ele.getAttribute("data-height"));

// 新版浏览器会支持dataset属性,可以通过元素DOM的dataset,获取对应的data-属性
// 但是要注意,获取的时候,只需要data-*后面的部分,并且这一部分需要转化为驼峰式
// 比如获取data-gender-test, 需要书写:ele.dataset.genderTest
console.log(ele.dataset.name);
console.log(ele.dataset.genderTest);

在CSS中我们可以通过以下方式获取data-属性中的值:

.data-ele::before {
    content: attr(data-parent);
}

.data-ele[data-columns='3'] {
  width: 400px;
}

.data-ele[data-columns='4'] {
  width: 600px;
}

参考文章:使用数据属性

2. 你有用过CSS预处理器吗?喜欢用哪个?原理是什么?

它能让你的CSS具备更加简洁、适应性更强、可读性更强、层级关系更加明显、更易于代码的维护等诸多好处。 CSS预处理器种类繁多,目前Sass、Less、用的比较多。 使用功能:

  • 嵌套:反映层级和约束
  • 变量和计算: 减少重复代码
  • Extend 和 Mixin 代码片段 (用的少)
  • 循环:适用于复杂有规律的样式
  • import css 文件模块化

原理:通过字符串的替换,根据CSS语法规范将sass、less替换成css。底层原理涉及到AST抽象语法树,有兴趣可以了解下。

3. 如何快速让一个数组乱序,写出来

// 我的算法实现,空间和时间复杂度比较高

let arr = [1, 2, 3, 4, 5, 6, 7];

console.log(disSortArray(arr));

function disSortArray(originalArr) {
    if (!originalArr || !(originalArr instanceof Array)) {
        return [];
    }

    let sortIndexArr = [];
    let randomNum = 0;
    let disSortedArr = [];

    while(sortIndexArr.length <= originalArr.length - 1) {
        randomNum = getRandomNum(0, originalArr.length - 1);
        if (!sortIndexArr.includes(randomNum)) {
            sortIndexArr.push(randomNum);
        }
    }

    sortIndexArr.forEach(index => {
        disSortedArr.push(originalArr[index]);
    });
    return disSortedArr;
}

function getRandomNum(start = 0, end = 0) {
    return Math.floor(Math.random() * (end - start + 1)) + start;
}


// 经典洗牌算法

function shuffle(array) { 
    let arrayLength = array.length,   
        randomIndex, //随机数   
        tempItem; //临时存储元素  
    for (let i = arrayLength - 1; i >= 0; i--) {    
        randomIndex = Math.floor(Math.random() * (i + 1));    
        tempItem = array[randomIndex];    
        array[randomIndex] = array[i];    
        array[i] = tempItem;  
    }  
    return array;
}
console.log(shuffle(arr));

2020-07-27

1. 请说说<script><script async><script defer>的区别

  • <script> : 遇到此标签之前,浏览器会暂定解析执行该标签后面的HTML,而是记性加载该标签中的js文件,加载完成之后立即执行该js文件。完成之后继续解析该标签后续的HTML。
  • <script async> : 加载该标签中的js文件和解析后面HTML文件是并行进行的(异步),js文件加载完成之后,立即执行,此时后续HTML的解析会暂定。等js文件执行完成之后,浏览器再继续解析后续的HTML。
  • <script defer> : 加载该标签中的js文件和解析后续HTML文件是并行进行的(异步),但是浏览器会等后续HTML全部解析完成之后,再执行该js文件。

详情可以参考文章:defer和async的区别

2. 在页面中的应该使用奇数还是偶数的字体?为什么呢?

  • 常用偶数号字体,但奇数号字体也没关系,例如:知乎正文使用15px字体,豆瓣电影使用13px字体
  • UI设计师导出的设计稿一般都是偶数号字体
  • 偶数字号容易和页面其他标签的其他属性形成比例关系
  • Windows 自带的点阵宋体(中易宋体)从 Vista 开始只提供 12、14、16 px 这三个大小的点阵, 而 13、15、17 px 时用的是小一号的点阵(即每个字占的空间大了 1 px,但点阵没变),于是略显稀 疏。(没试过)

3. 写一个判断设备来源的方法

大致思路:利用 window.navigator.userAgent 属性字符串进行判断,例如:

"Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/84.0.4147.89 Safari/537.36"

这里给出一个实例:

function deviceType() {
    let device = "";
    let ua = navigator.userAgent;
    let agent = ["Android", "iPhone", "SymbianOS", "Windows Phone", "iPad", "iPod"];
    for (var i = 0; i < agent.length; i++) {
        if (ua.indexOf(agent[i]) > 0) {
            device = agent[i]
            break
        }
    }
    return device;
}

如果是在实际项目中,建议使用成熟的第三方库:GitHub - current-device

2020-07-28

1. 说说你对影子(Shadow)DOM的了解

Shadow DOM 可以想象成我们在 Vue 或者 React 中使用的一个个组件,是一种将 HTML 结构、Style 封装起来的结构。我们熟悉的 video 标签,其实就是 Shadow DOM 的封装。

详情可以参考以下文章:

2. 修改chrome记住密码后自动填充表单的黄色背景

chrome 表单自动填充后,input文本框的背景会变成黄色的,通过审查元素可以看到这是由于chrome会默认给自动填充的input表单加上input:-webkit-autofill私有属性,然后对其赋予以下样式:

input:-webkit-autofill, textarea:-webkit-autofill, select:-webkit-autofill {
    background-color: rgb(250, 255, 189); /* #FAFFBD; */
    background-image: none;
    color: rgb(0, 0, 0);
}

3. 说说你对arguments的理解,它是数组吗?

arguments 是一个对象,不是一个数组。其特性如下:

  • arguments和function是分不开的,JS中每一个函数都包含这个实例,他引用者函数的实参。
  • arguments虽然不是一个数组,但是可以通过数组下标的形式访问函数的实参,比如:arguments[1]
  • arguments.callee 是函数自身的引用

2020-08-03

1. 说说你对 <meta> 标签的理解

直译过来就是元数据标签,这是一个辅助性标签,其中的内容不会在页面上显示,但是通过这个标签,我们可以设置网页的一些基本信息。比如:

  • 设置网页的编码方式
  • 定义视口的宽度以及缩放比(常用于移动端开发)
  • 指定网页的描述,关键词等信息,有利于SEO

具体信息可以参考文章:菜鸟教程-meta标签移动Web开发基础-meta锦集

2. rgba()和opacity这两个的透明效果有什么区别呢

  • opacity 是属性,rgba()是函数,计算之后是个属性值;
  • opacity 作用于元素和元素的内容,内容会继承元素的透明度,取值0-1;
  • rgba() 一般作为背景色 background-color 或者颜色 color 的属性值,透明度由其中的 alpha 值生效,取值0-1;

3. 解释下面这段代码的意思

[].forEach.call($$("*"),function(a){ a.style.outline="1px solid #"+(~~(Math.random()*(1<<24))).toString(16) })

**代码作用: ** 获取了所有的页面元素,然后使用一个不同的颜色为它们添加了一个1px的边框。

代码解析:

  • [].forEach.call() :调用引用数组的 forEach 方法
  • $$('*') document.querySelectorAll('*')
  • ~~aparseInt(a)
  • 1<<24 : 对二进数1小数点右移24位
  • (parseInt(Math.random()*(1<<24)).toString(16)) : 获得了一个位于0-16777216之间的随机整数,也就是随机颜色,再使用toString(16)将它转化为十六进制数。

2020-07-28

1. 你了解什么是无障碍web(WAI)吗?在开发过程中要怎么做呢?

无障碍 web 是指能让视觉障碍的人也能根据屏幕阅读器的提示阅读网页。这一块只知道一个大致概念,国内使用较少(甚至还遇到过加了 title 被测试提 bug 的情况)

目前能想到的只有下面几点:

  • 尽可能地使用语义化标签,如 <selection>, article 等标签
  • img 标签添加 alt
  • button 或者按钮上添加 title
  • 表单尽量使用 label for 可以和控件的 id 进行关联

2. 请描述css的权重计算规则

权重列表:

选择器案例权重值
!important!importantInfinity
内联样式style=".."1000
ID#id100
class.class10
属性[type='text']10
伪类:hover10
标签p1
伪元素::first-line1
相邻选择器、子代选择器、通配符* > +0

比较规则:

  • 1000>100。也就是说从左往右逐个等级比较,前一等级相等才往后比。
  • 在权重相同的情况下,后面的样式会覆盖掉前面的样式。
  • 继承属性没有权重值。
  • 通配符、子选择器、相邻选择器等的。虽然权值为0,但是也比继承的样式优先。
  • ie6以上才支持important,并且尽量少用它。

3. 写一个获取数组的最大值、最小值的方法

const getMinAndMax = arr => ({
    // 数组展开在 ES5 中可以用 apply 代替
    // ES5: Math.min.apply(null, arr)
    min: Math.min(...arr),
    max: Math.max(...arr)
});

2020-08-05

1. 网页上的验证码是为了解决什么问题?说说你了解的验证码种类有哪些

验证密码解决的问题:

  • 防止机器行为,确保是人为操作,比如登录系统,发送动态
  • 保护服务器,防止通过代码或工具进行爆刷
  • 保护用户隐私,防止暴力破解账号密码

验证码的种类:

  • 图形验证码
  • 手机验证码
  • 数字计算验证码
  • 识别图形验证码

2. 描述下你所了解的图片格式及使用场景

GIF

优点:GIF是动态的;支持无损耗压缩和透明度。

缺点:的详细的图片和写实摄影图像会丢失颜色信息;在大多数情况下,无损耗压缩效果不如 JPEG 格式或 PNG 格式;GIF 支持有限的透明度,没有半透明效果或褪色效果。

适用场景:主要用于比较小的动态图标。

PNG

优点:PNG格式图片是无损压缩的图片,能在保证最不失真的情况下尽可能压缩图像文件的大小;图片质量高;色彩表现好;支持透明效果;提供锋利的线条和边缘,所以做出的logo等小图标效果会更好;更好地展示文字、颜色相近的图片。

缺点:占内存大,会导致网页加载速度慢;对于需要高保真的较复杂的图像,PNG虽然能无损压缩,但图片文件较大,不适合应用在Web页面上。

适用场景:主要用于小图标或颜色简单对比强烈的小的背景图。

JPG

优点:占用内存小,网页加载速度快。

缺点:JPG格式图片是有损压缩的图片,有损压缩会使原始图片数据质量下降,即JPG会在压缩图片时降低品质。

适用场景:由于这种格式图片对色彩表现比较好,所以适用于色彩丰富的图片。主要用于摄影作品或者大的背景图等。不合适文字比较多的图片。

SVG

优点:SVG是矢量图形,不受像素影响,在不同平台上都表现良好;可以通过JS控制实现动画效果。

缺点:DOM比正常的图形慢,而且如果其结点多而杂,就更慢;不能与HTML内容集成。

适用场景:主要用于设计模型的展示等。

WebP

优点:WebP格式,谷歌(google)开发的一种旨在加快图片加载速度的图片格式。图片压缩体积大约只有JPEG的2/3,并能节省大量的服务器宽带资源和数据空间。

缺点:相较编码JPEG文件,编码同样质量的WebP文件需要占用更多的计算资源。

适用场景:WebP既支持有损压缩也支持无损压缩。将来可能是JPEG的代替品。

3. 写一个方法判断字符串是否为回文字符串

// 遍历比较数组的一半
function testStr(_str) {
    _str = _str.toLowerCase().replace(/[^a-zA-Z0-9]/g, "");
    let isHuiWen = true;

    for (let i = 0; i < Math.floor(_str.length / 2); i++) {
        if (_str[i] !== _str[_str.length - 1 - i]) {
            isHuiWen = false;
            break;
        }
    }
    return isHuiWen;
}

// 直接比较翻转后的字符串
var isPalindrome = function(s) {
    if (s.length === 1) return true
    const str = s.replace(/[^a-zA-Z0-9]/g, "").toLowerCase()
    const strReverse = str.split('').reverse().join('')
    return str === strReverse
};

2020-08-07

1. DOM和BOM有什么区别?

BOM是Browser Object Model的缩写,即浏览器对象模型。DOM是Document Object Model的缩写,即文档对象模型。他们都是浏览器提供给JavaScript的API接口。

BOM指浏览器对象模型 : 提供了独立于内容而与浏览器窗口进行交互的对象。描述了与浏览器进行交互的方法和接口,可以对浏览器窗口进行访问和操作,譬如可以弹出新的窗口,改变状态栏中的文本。

DOM指文档对象模型 : DOM 是针对 HTML 的基于树的 API。描述了处理网页内容的方法和接口,是 HTML 的API,DOM 把整个页面规划成由节点层级构成的文档。

注意: 只有 JS 的宿主环境是浏览器的时候才有 DOM 和 BOM ,在 Node 中是没有这两个对象的。

2. 让网页的字体变得清晰,变细用CSS怎么做?

让文字变细有两个要素:

  • font-weight + font-family font-weight 来控制粗细还是需要看对应的字体有没有对应的变种字体。因此这就和 font-family 相关。
  • -webkit-font-smoothing 这个属性是 Chrome 的抗锯齿属性。加上后会显得细一些,但是只针对 webkit 内核的浏览器才有效。

要理解CSS能通过font-weight设置字体的粗细, 首先要明白CSS字体的基本设定. 以字体Times字体为例, Times实际是一个字体系列, 它由多种字体变形组合而成, 包括 TimesRegular, TimesBold, TimesItalic等. 每种变形都是一种具体的字体风格(font face).

当font-weight变小时, 浏览器会在指定字体系列中, 找到更细的字体变种. 因而如果使用的字体系列中, 只有一种变种, 则无论font-weight怎么变化, 字体的粗细都不会有变化的

因此文字的粗细还跟font-family有关

但就算设置了以上两项, 我在Mac的Chrome浏览网页时, 还是觉得文字有点”粗”. 这种”粗”用专业的话来说就是, “字体存在半个像素的锯齿,浏览器渲染的时却直接显示一个像素”, 则此时需要对文字进行”抗锯齿处理”. 也即设置为

参考代码:

-webkit-font-smoothing: antialiased
-moz-osx-font-smoothing: grayscale
text-shadow: 1px 1px 1px 1px rgba(0,0,0,0.005)
text-rendering: optimizeLegibility

3. 写一个方法把0和1互转(0置1,1置0)

function change(num) {
    return Number(!num);
}

2020-08-11

1. 说说你对HTML元素的显示优先级的理解

帧元素(frameset) 优先级最高 >>> 表单元素 > 非表单元素,即 input type="radio" 之类的表单控件 > 普通的如 a,div 等元素。

从有窗口和无窗口元素来分,有窗口元素 > 无窗口元素。有窗口元素如 Select 元素、Object 元素。

z-index 属性也可以改变显示优先级,但只对同种类型的元素才有效。

2. 说下line-height三种赋值方式有何区别?

line-height 可以有带单位及不带单位的写法(感觉其实是两种)。

div {
    line-height: 24px;
    line-height: 1.5;
    line-height: 1.5em;
    line-height: 150%;
}

对于应用css在单个元素上,这几种写法的效果都是一样的(除了 px 需要一些计算)。但由于 line-height 是可以被继承的,因此会影响内部子元素的 line-height。简单的可以总结为:

  • 带有单位的 line-height 会被计算成 px 后继承。子元素的 line-height = 父元素的 line-height * font-size (如果是 px 了就直接继承)
  • 而不带单位的 line-height 被继承的是倍数,子元素的 line-height = 子元素的 font-size * 继承的倍数

参考文章:line-height 3种设置方式的区别

3. 造成内存泄漏的操作有哪些?

  • 死循环
  • 过度递归
  • 对页面中的一些副作用没有清除
  • 闭包中的变量没有被回收,造成内存泄露

2020-08-21

1. html和html5有什么区别呢?

  • HTML5简化了很多细微的语法,例如doctype的声明,只需要写就行了。
  • 增加了许多语义化的标签,从而更利于seo,比如: header、footer、section、article等
  • 增加了许多新功能,如canvas、video、SVG

2. 用CSS绘制一个三角形

设置宽高为0,边框一定的宽高,然后设置各个边框的背景色。具体可以参考文章: CSS 绘制各种形状

3. 说说你对this的理解

javaScript 中的 this 用一句话来概括,就是在执行时确定的。从现象上来看,就是谁调用了某个方法,那么这个方法中的 this 指向谁。

下面是最常见的例子:

const obj = {
    sayThis: function() {
        console.log(this);
    }
};

obj.sayThis(); // obj
const globalSay = obj.sayThis;
globalSay(); // window 浏览器中的 global 对象

谁调用了某个方法,那么这个方法中的 this 指向谁

这个“谁”我们可以通过 . 操作符来判断。比如 obj.sayThis(),这里就是 obj 调用了 sayThis 方法,所以 this 指向 obj。而后一个 globalSay() 是直接调用的,在 JavaScript 中会把这个方法绑在全局(window)上,所以本质就是 window.globalSay(),自然这里的 this 就指向了 window

JavaScript 给我们提供了 apply/call/bind 三种方法来改变 this 的指向。在 ES6 的语法中还提供了箭头函语法,让我们在代码书写时就能确定 this 的指向(编译时绑定)。唯一需要注意的就是要避开箭头函数带来的坑。

把上面的例子改为箭头函数,结果完全不同。

const obj = {
    sayThis: () => {
        console.log(this);
    }
};

obj.sayThis(); // window 因为 JavaScript 没有块作用域,所以在定义 sayThis 的时候,里面的 this 就绑到 window 上去了
const globalSay = obj.sayThis;
globalSay(); // window 浏览器中的 global 对象

参考文章:全方位解读 this

2020-08-23

1. Standards模式和Quirks模式有什么区别?

怪异模式和标准模式最早是为了对旧版本网页进行兼容而设计的,可以通过 <!DOCTYPE> 来进行区分。两者最主要的区别就是在盒子模型上,元素的宽度。

在标准模式下,元素的宽度只是指 width,如果添加了 paddingborder 元素实际的宽度需要加上 paddingborders。

在怪异模式下,元素的 width 是包含了 paddingborder

通过 CSS 的 { box-sizing: border-box; } 来对盒模型进行设置。

虽然标准模式可以算是标准,但实际使用过程中怪异模式反而更符合人的直觉(个人认为),这样可以减少对 paddingborder 的额外计算。

2. 浏览器是怎样判断元素是否和某个CSS选择器匹配?

先产生一个元素集合,然后从右向左判断;

浏览器先产生一个元素集合,这个集合往往由最后一个部分的索引产生(如果没有索引就是所有元素的集合)。然后向上匹配,如果不符合上一个部分,就把元素从集合中删除,直到真个选择器都匹配完,还在集合中的元素就匹配这个选择器了。

2020-08-25

1. 用一个div模拟textarea的实现

主要是利用了 HTML5 提供的 contenteditable 属性,让普通的 div 可以进行编辑。结合 CSS 可以做到拉伸、滚动等效果。

如果设置contenteditable="true" 属性后,如果直接复制html内容的话会出现把样式也复制进去。如果不需要该需求的话可以设置 contenteditable="plaintext-only"就可以了,这个属性代表只可输入纯文本,但是复制的格式还是存在的。

contenteditable 属性可以设置这几个值:"events", "caret", "typing", "plaintext-only", "true", and "false"

<!DOCTYPE html>
<html>
    <head>
        <title>用一个div模拟textarea的实现</title>
    </head>
    <style>
        .edit{
            width: 300px;
            height: 200px;
            padding: 5px;
            border: solid 1px #ccc;
            resize: both;
            overflow:auto;
        }
    </style>
    <body>
        <h3>用一个div模拟textarea的实现</h3>
        <div class="edit" contenteditable="true">
            这里是可以编辑的内容,配合容器的 overflow ,多行截断,自定义滚动条,简直好用的不要不要的。
        </div>
    </body>
</html>

2. 使用flex实现三栏布局,两边固定,中间自适应

使用flex布局,主要涉及到 flex-grow, flex-shrink, flex-basis 等属性的使用。具体解释可以参考:Flex 布局教程:语法篇

<div class="container">
    <section class="left red"></section>
    <section class="middle blue"></section>
    <section class="right red"></section>
</div>

<style>
    .container {
        width: 100%;
        height: 100%;
        display: flex;
    }

    .left, right {
        flex: 0 0 auto;
        width: 50px;
        height: 100%;
    }

    .middle {
        flex: 1 1 auto;
        height: 100%;
    }

    .red {
        background-color: red;
    }

    .blue {
        background-color: blue;
    }
</style>

3. 请你解释一个为什么 10.toFixed(10) 会报错

在我们的直觉上,10.toFixed(10) 是把整数的 10 转为浮点数并且保留 10 位小数部分。

但实际上会出错,是因为 JS 的解释器对 . 操作符产生了歧义。在 JS 中 . 可以表示小数和从对象中取值。在这个例子中, 由于 10 是整数,所以在 10. 默认是小数点,因此会报错。

解决的办法有下面几种:

  • (10).toFixed(10) 个人喜欢这种,看起来舒服一点

  • 10..toFixed(10)

2020-09-07

1. HTML与XHTML二者有不同

XHTML 是更严谨更纯净的 HTML 版本, 所以会更加严谨,表现在:

  • XHTML 标签必须关闭
  • XHTML所有标签必须小写
  • XHTML标签必须正确嵌套

2. 写出主流浏览器内核私有属性的css前缀

浏览器内核CSS前缀
ChromeBlink内核(新)-webkit-
FirefoxGecko内核-moz-
SafariWebkit内核-webkit-
OperaWebkit内核(新)-o-
IE/EdgeTrident内核-ms-

谷歌(新的内核为Blink)、Safari,新版Opera浏览器,以及几乎所有IOS系统中的浏览器(包括IOS中的火狐浏览器),简单的说,所有基于WebKit内核的浏览器的前缀都采用-webkit-

3. 请手写一个幻灯片的效果

思路一 :元素并排浮动 改变offset 思路二 :position 层叠 改变z-Index

2020-09-08

1. html5哪些标签可以优化SEO

优化 SEO 应该是可以给爬虫有比较明确的含义的标签。尽可能地不要使用 div 到底。

  • meta: meta 标签中的 keywords 和 description
  • h1-h6
  • nav
  • section
  • article
  • footer
  • header

2. 不使用border画出1px高的线,在不同浏览器的标准和怪异模式下都能保持效果一样

可以利用块级元素的高度来进行设置,比如:

.box2 {
    background-color: #000;
    height: 1px;
}

.box3:after{
    content: '';
    display: block;
    height: 1px;
    background-color: #000;
}

3. 找到字符串中最长的单词,并返回它的长度

参考答案:找到字符串中最长的单词,并返回它的长度

2020-09-09

1. 说说你对cookie和session的理解

两者作用:会话保持的功能,为了解决http无状态的问题。

cookie:用户通过HTTP第一次访问一个服务器的时候,服务器就会把一个cookie返回给客户端,保存在客户端的内存或者硬盘中,同一个用户下次再访问服务器时,就把cookie带上,这样服务器就认出这个用户了。

session理解:有了session之后,用户只需要携带一个默认名为 JSEESIONID 的cookie去访问服务器,它的 value 是每个用户的唯一ID。用户第一次访问服务器,会生成这个cookie,并且在服务器端实例化一个 HttpSession 对象,这个对象其实就是个Map,可以用来保存用户的信息。下一次用户再访问服务器,就可以根据ID找到这个session,并读取其中保存的用户信息。

区别:

安全性:cookie保存在客户端,可在本地查看修改,安全性不高。session的用户信息保存在服务器端,发给客户端的只是一个用户id,相对更安全 限制:cookie有大小和数量限制,session没有大小限制,只有时间限制

3. 实现单行文本居中和多行文本左对齐并超出显示"..."

  • 单行文本居中。在 webkit 内核中适用。非 webkit 内核,可以是用 js 或者用 ::after 模拟。

    .single-text{
        width: 500px;
        font-size: 18px;
        font-weight: bold;
        text-align: center;
        color: white;
        background: lightblue;
        display: box;
        white-space: nowrap;
        overflow:hidden;
        text-overflow: ellipsis;
    }
    
  • 多行文本左对齐。多行文本没有很好的解决方法,只能依赖 js 或者 css 的相对定位。

    .multi-text{
        width: 50%;
        height: 4.5rem;
        line-height: 1.5;
        padding: 20px;
        background: lightblue;
        overflow: hidden;
        position: relative;
        box-sizing: border-box;
    
        &::after{
            content: '...';
            height: 1.5rem;
            position: absolute;
            bottom: 5px;
            right: 5px;
        }
    }
    

参考文章:可能是最全的 “文本溢出截断省略” 方案合集

3. 说说你对eval的理解

eval() 相当于一个小型的js解析器,接受一个字符串,可以把字符串解析成js代码并执行,所以有很有大的安全隐患,并且写进去的代码都是字符串,不利于维护,使用它执行代码性能也会大大折扣,所以正常情况下不建议使用。