JS由哪三部分组成?
-  ECMAScript:JS的核心内容,描述了语言的基础语法,比如var,for,数据类型(数组、字符串) 
-  文档对象模型(DOM):DOM把整个HTML页面规划为元素构成的文档 
-  浏览器对象模型 (BOM):对浏览器窗口进行访问和操作 
一元运算符、二元运算符和三元运算符
-  一元运算符:正号+、负号-、++、-- 
-  二元运算符:算术运算符(加减乘除)、关系运算符(==、!=、>、<) 
-  三元运算符:唯一的具有三个操作数的运算符。 条件 ? 表达式1 : 表达式2如果条件为真,则返回表达式1的值,否则返回表达式2的值。
条件语句
-  switch-case-default -  要判断某一个变量 等于 某一个值的时候使用 
-  必须写break 
-  性能好,可以精准匹配 
 switch (要判断的变量) {case 情况1:情况1要执行的代码break;case 情况2:情况2要执行的代码break; default:上述情况都不满足的时候执行的代码 }  let code = 1switch (code) {case 0:document.write('未付款');break;case 1:document.write('已付款');break;case 2:document.write('已发货');break;case 3:document.write('已完成');break; default:document.write('未知状态'); }
-  
-  while -  当条件满足时执行,一旦不满足就不执行 
-  语法: while(条件){满足添加就执行}
-  满足条件就执行,所以我们写的时候要设定一个边界值,不然会出现死循环 
 
-  
-  do-while -  和while类似,但是do-while循环是先不管条件,直接执行一次,然后再开始进行条件判断 
-  语法: do{要执行的代码} while (条件)
 
-  
-  for循环 -  也是循环的结构 
-  语法: for(var i=0;i<10;i++){要执行的代码}(把初始化,条件判断,自身改变) 写在一起了 -  先赋初始值,然后判断,符合条件执行代码,执行完改变自身,然后再赋值再判断,以此类推 
 
-  
 
-  
JS有哪些内置对象?
-  数据封装类对象: Object、Array、Boolean、Number、String
-  其他对象: Function、Arguments、Math、Date、RegExp、Error
-  ES6新增对象: Symbol、Map、Set、Promise、Proxy、Reflect
-  常用的有: -  Math: -  Math.max():返回一组数字中的最大值。
-  Math.min():返回一组数字中的最小值。
-  Math.abs():返回一个数的绝对值。
-  Math.sqrt():返回一个数的平方根。
 
-  
-  Date: -  new Date():创建一个表示当前日期和时间的 Date 对象。
-  getFullYear():获取 Date 对象的年份。
-  getMonth():获取月份(0-11,0 表示一月)。
-  getDate():获取日期(1-31)。
-  getDay():获取星期几(0-6,0 表示星期日)。
-  getHours():获取小时(0-23)。
-  getMinutes():获取分钟(0-59)。
-  getSeconds():获取秒(0-59)。
-  getTime():返回自 1970 年 1 月 1 日 00:00:00 UTC 起至当前时间的毫秒数。
-  setFullYear():设置年份。
-  setMonth():设置月份。
-  setDate():设置日期。
-  setHours():设置小时。
-  setMinutes():设置分钟。
-  setSeconds():设置秒。
 
-  
-  Array: -  concat():连接两个或多个数组,并返回一个新数组。
-  join():将数组中的所有元素连接成一个字符串。
-  pop():删除并返回数组的最后一个元素。
-  push():向数组的末尾添加一个或多个元素,并返回新的长度。
-  shift():删除并返回数组的第一个元素。
-  unshift():向数组的开头添加一个或多个元素,并返回新的长度。
-  reverse():颠倒数组中元素的顺序。
-  sort():对数组进行排序。
-  slice():选取数组的一部分,并返回一个新数组。
-  splice():删除、替换或插入元素到数组中,并返回被删除的元素组成的新数组。
-  indexOf():返回指定元素在数组中首次出现的索引。
-  lastIndexOf():返回指定元素在数组中最后一次出现的索引。
-  forEach():对数组中的每个元素执行一个函数。// 1.没有返回值 // 2.不能使用break // 3.遍历的是item let arr = ['a','b','c'] let res = arr.forEach(item=>{console.log(item)break;return item + '0' }) console.log(res)
-  map():对数组中的每个元素执行一个指定的函数,并返回一个新数组。// 1.有返回值(数组)默认return是undefined // 2.接受的参数是一个函数(key,value) // 3.不能用break打断 let arr = ['a','b','c'] let res = arr.map((value,key)=>{return value + '0' }) console.log(res)
-  filter():根据指定条件过滤数组中的元素,并返回一个新数组。let a = [1,2,3,14,15] // current当前值;index当前值的下标;array这个数组对象 let b = a.filter((current,index,array)=>{return current > 10 }) console.log(a) console.log(b)
-  reduce():从左到右对数组中的每个元素执行一个归并操作,返回一个累计的值。
-  reduceRight():从右到左对数组中的每个元素执行一个归并操作,返回一个累计的值。
-  some():检查数组中是否至少有一个元素满足指定条件。
-  every():检查数组中的所有元素是否都满足指定条件。
-  find():返回数组中满足指定条件的第一个元素。
-  findIndex():返回数组中满足指定条件的第一个元素的索引。
-  includes():判断数组是否包含指定元素。
-  toString():将数组转换为字符串,并返回结果。
-  isArray():用于检测一个值是否为数组。
 Vue中的7个变异方法: pop()、push()、shift()、unshift()、reverse()、sort()、splice()
-  
-  String: -  length:返回字符串的长度。
-  charAt():返回指定索引位置的字符。
-  concat():连接两个或多个字符串,并返回新的字符串。
-  substring():返回一个新的字符串,包含从开始索引到结束索引之间的字符。
-  toUpperCase():将字符串中的字母转换为大写。
-  toLowerCase():将字符串中的字母转换为小写。
-  trim():去除字符串两端的空白字符。
-  split():将字符串拆分为一个字符串数组,根据指定的分隔符进行拆分。
-  replace():替换字符串中的某个子字符串为另一个字符串。
-  startsWith():检查字符串是否以指定的子字符串开头。
-  endsWith():检查字符串是否以指定的子字符串结尾。
-  includes():检查字符串是否包含指定的子字符串。
-  charAt():获取字符串中指定索引位置的字符。
-  charCodeAt():获取字符串中指定索引位置的字符的 Unicode 编码值。
-  indexOf():返回指定子字符串在字符串中第一次出现的索引位置。
-  lastIndexOf():返回指定子字符串在字符串中最后一次出现的索引位置。
 
-  
 
-  
ES6有哪些新特性
-  新增了块级作用域:let和const 
-  箭头函数 
-  扩展运算符和剩余参数 ...
-  解构赋值 
-  模板字符串`` 
-  数据类型和数据结构:symbol、set、map 
-  新增的对象、方法等,promise、proxy、Reflect等等 
JS的数据类型
基本数据类型
-  保存在栈内存中,保存的是具体的值。栈是线性数据结构 
-  String、Number、Boolean、null、undefined 
引用数据类型
-  保存在堆内存中,声明一个引用类型变量时,保存的是引用数据类型的地址。堆是树形结构 
-  Array、Function、Object、正则、日期等 
-  例如,声明两个引用类型同时指向了一个地址的时候,修改其中一个那么另外一个也会改变 
JS对数据类型的检测方法有哪些
-  typeof():可以返回一个值的基本数据类型。只能判断基本数据类型,不能判断引用数据类型 
-  instanceof():可以用来检查一个对象是否是某个构造函数的实例。只能判断引用数据类型,不能判断基本数据类型。语法例如是 'abc' instanceof String
-  constructor:检查一个对象的 constructor属性来确定它的类型。('abc').constructor === String
-  Object.prototype.toString.call():返回一个值的详细类型信息,包括基本数据类型和对象类型。 
-  Array.isArray:判断数组,如果是返回true 
隐式类型转换和强制类转换
-  强制类型转换: -  Number():把值转换成数字 
-  String():把值转换成字符串 
-  Boolean():把值转换成布尔值 
-  parseInt():将字符串转换为整数 
-  parseFloat():将字符串转换成浮点数 
-  Array.from():将类数组对象或可迭代对象转换成真正的数组 
 
-  
-  隐式类型转换:js执行代码自动转换 -  数字和字符串:+结果为字符串;-、*、/时结果为数字 
-  等号运算符比较不同的类型值,会被转换成相同的类型 
-  数字和null:null转换为0 
-  数字和undefined:undefined转换为NAN 
 
-  
1+‘2’ 和 1-‘2’ 的结果
-  1+‘2’ 是“12”,做了拼接 
-  1-‘2’ 是 -1,当做减法时,js会尝试将字符串类型的2转成数值类型的2,所以就是-1 
toString和String的区别
-  toString:是所有JS对象的方法,可以将任何类型的值转换为字符串。如果是null或undefined调用这个方法会输出 [object Undefined] 
-  string:是一个全局函数,只能将非null和undefined值转换为字符串 
let、const和var的区别
-  变量的作用域: -  let和const声明的变量具有块级作用域 
-  var声明的变量存在变量提升,函数级作用域 
 
-  
-  变量重复声明 -  let和const声明的变量不允许被重复声明 
-  var声明的变量可以被重复声明,后面声明的覆盖前面声明的 
 
-  
-  变量的赋值 -  var和let声明的变量可以进行重新赋值 
-  const声明的变量是常量,不可以进行赋值 
 
-  
-  暂时性死区:避免变量在使用前就被意外地引用或访问 -  var不存在暂时性死区 
-  let和const存在暂时性死区,只有等到声明变量的那一行代码出现,才可以获取和使用该变量,否则报错 
 
-  
const声明数组可以push元素吗?
可以的。虽然const声明的变量是常量,意味着引用是不能修改的,也就是不能将其重新赋值为另一个数组。但是可以修改数组本身的内容,进行增删改操作。
数组常见方法
-  push(): 在数组末尾添加一个或多个元素,并返回新数组的长度。
-  pop(): 移除并返回数组末尾的元素。
-  unshift(): 在数组开头添加一个或多个元素,并返回新数组的长度。
-  shift(): 移除并返回数组开头的元素。
-  concat(): 合并两个或更多数组,并返回新的合并后的数组,不会修改原始数组。
-  slice(): 从数组中提取指定位置的元素,返回一个新的数组,不会修改原始数组。
-  splice(): 从指定位置删除或替换元素,可修改原始数组。
-  indexOf(): 查找指定元素在数组中的索引,如果不存在则返回-1。
-  lastIndexOf(): 从数组末尾开始查找指定元素在数组中的索引,如果不存在则返回-1。
-  join(): 将数组中的所有元素转为字符串,并使用指定的分隔符连接它们。
-  reverse(): 颠倒数组中元素的顺序,会修改原始数组。
-  sort(): 对数组中的元素进行排序,默认按照字母顺序排序,会修改原始数组。
-  循环的方法: -  filter 
-  forEach 
-  map 
-  some 
-  every 
-  reduce 
 
-  
数组新增了哪些扩展?
-  扩展运算符(Spread operator):使用 ...语法可以将一个数组展开成多个独立的元素,或者将多个元素合并为一个数组。
-  Array.from():通过类似数组的对象或可迭代对象创建一个新的数组。 
-  Array.of():创建一个由传入参数组成的新数组。 
-  find() 和 findIndex():用于在数组中查找满足指定条件的第一个元素及其索引。 
-  includes():检查数组是否包含指定的元素,并返回布尔值。 
-  fill():使用指定的值填充数组的所有元素。 
-  flat() 和 flatMap():用于将嵌套的数组展平,减少维度。 
-  以下方法的回调函数支持箭头函数语法。 -  filter(): 创建一个新数组,其中包含符合条件的所有元素。
-  map(): 创建一个新数组,其中包含对原始数组中的每个元素进行操作后的结果。
-  reduce(): 将数组中的元素进行累积操作,返回一个单一的值。
-  forEach(): 对数组中的每个元素执行提供的函数。
 
-  
-  entries()、keys() 和 values():用于遍历数组的键值对、键和值。 
-  数组解构赋值:可以通过解构赋值从数组中提取值并赋给变量。 
-  数组的扩展属性: Array.prototype.length可以被修改,Array.prototype[@@toStringTag]返回"Array"
数组去重方法
-  使用new Set:用于存储一组唯一的值。使用new Set()将数组转为Set,再使用Array.from()转换为数组实现去重 const res1 = Array.from(new Set(arr)); 
-  for + indexOf:遍历数组,将当前元素与前面的元素进行比较,如果前面已经存在该元素,则跳过,否则将该元素添加到新数组中。 const unique2 = arr => {const res = [];for (let i = 0; i < arr.length; i++) {if (res.indexOf(arr[i]) === -1) res.push(arr[i]);}return res; }
-  filter + indexOf方法:筛选出不重复的元素,返回一个新的数组 const unique4 = arr => {return arr.filter((item, index) => {return arr.indexOf(item) === index;}); }
-  for + includes const unique3 = arr => {const res = [];for (let i = 0; i < arr.length; i++) {if (!res.includes(arr[i])) res.push(arr[i]);}return res; }
-  两层for循环+splice const unique1 = arr => {let len = arr.length;for (let i = 0; i < len; i++) {for (let j = i + 1; j < len; j++) {if (arr[i] === arr[j]) {arr.splice(j, 1);// 每删除一个树,j--保证j的值经过自加后不变。同时,len--,减少循环次数提升性能len--;j--;}}}return arr; }
数组排序的方法
-  sort() -  默认情况下, sort()方法会将数组中的元素转换成字符串,并按照 Unicode 编码顺序进行排序。arr = [1,2,12,25,112] console.log(arr.sort()); // [1, 112, 12, 2, 25] 
-  常用方法,可以传递一个比较函数作为参数,以自定义排序方式。 arr = [1, 2, 12, 25, 112] // 升序 arr.sort(function (a, b) {return a - b }) console.log(arr); // [1, 2, 12, 25, 112]  // 降序 arr.sort(function (a, b) {return b - a }) console.log(arr); // [112, 25, 12, 2, 1]
 
-  
-  reverse():反转数组,也就是逆置 
-  冒泡排序 -  通过不断比较相邻的两个元素,将较大(或较小)的元素逐步向右(或向左)移动,就像气泡在水中慢慢上升一样,最终使得整个数组按照升序(或降序)排列。 function bubblingSort(arr) {// 外层循环负责循环的次数。由于最后一个一定是最大的数,所以最后一个可以不用排。因此循环的次数是length - 1for(var i = 0; i < arr.length - 1; i++) {// 内层循环负责两两比较for(var j = 0; j < arr.length - i - 1; j++) {// 如果发现前一个数比后一个数大,则交换位置if(arr[j] > arr[j + 1]) {var temp = arr[j]arr[j] = arr[j + 1]arr[j + 1] = temp}}}// 返回排好序的数组return arr; }
 
-  
-  快速排序 -  实现原理:先从数组中随便选择一个元素(通常是数组的第0项),作为基准元素。然后循环数组,把比基准元素小的放左边,比基准元素大的放右边 function fastSort(arr) {// 如果只有一个元素直接返回if(arr.length <= 1) return arr;// 假设第0个元素就是标杆var pivot = arr[0];// 声明两个数组比标杆元素小的放左边,比标杆元素大的放右边var left = [];var right = [];// 循环数组,比标杆元素小的放左边,比标杆元素大的放右边for(var i = 1; i < arr.length; i++) {if(arr[i] < pivot) {left.push(arr[i]);} else {right.push(arr[i]);}}// 递归调用,把比标杆元素小的放左边,比标杆元素大的放右边var arr2 = fastSort(left).concat(pivot, fastSort(right));// 改变原有数组中的元素for(var i = 0; i < arr2.length; i++) {arr[i] = arr2[i];}return arr; }
 
-  
-  选择排序 -  实现原理: -  遍历数组,将第一个元素设为当前最小元素。 
-  从第二个元素开始,依次与当前最小元素进行比较,找到最小的元素。 
-  将最小元素与当前位置的元素进行交换,将最小元素放置在已排序部分的末尾。 
-  重复上述步骤,每次从未排序的部分选择出一个最小元素放置在已排序部分的末尾,直到整个数组排序完成 
 
-  
 function selectSort(arr) {for(var i = 0; i < arr.length - 1; i++) {// 先假设第i个位置的元素是最小元素,然后保存其下标var minIdx = i;// 内层循环负责两两比较for(var j = i + 1; j < arr.length; j++) {// 如果发现有比假设的最小元素小的元素if(arr[j] < arr[minIdx]) {// 则立即更新最小位置的下标minIdx = j;}}// 交换位置var temp = arr[i];arr[i] = arr[minIdx];arr[minIdx] = temp;}return arr; }
-  
-  插入排序 -  实现原理:依次从数组中取出一个元素,然后从右向左依次查找,直到找到比它小的元素,将其插入到对应的位置 function insertSort(arr) {for (var i = 1; i < arr.length; i++) {// 依次从数组中取出一个元素var curValue = arr[i];// 指针依次向左移动一格(即从右向左依次查找)var j = i - 1;while(j >= 0 && curValue < arr[j]) {// 将当前找到的元素右移一格,空出当前的位置arr[j + 1] = arr[j];j--;}// 将当前找到的元素插入到正确的位置arr[j + 1] = curValue;}return arr; }
 
-  
-  归并排序 -  实现原理:先对数组进行拆分,拆分到每个数组中只有一个元素则停止拆分。然后在对拆分后数组按顺序进行合并 function mergeSort(arr) {// 如果数组的长度小于等于1,则直接返回if(arr.length <= 1) return arr;// 将数组从中间进行拆分var mid = Math.floor(arr.length / 2);// 递归拆分左边数组var left = mergeSort(arr.slice(0, mid));// 递归拆分右边数组var right = mergeSort(arr.slice(mid)); // 递归进行拆分合并var arr2 = merge(mergeSort(left), mergeSort(right));// 修改原数组for(var i = 0; i < arr2.length; i++) {arr[i] = arr2[i];}return arr; }  // 合并数组方法 function merge(left, right) {// 先声明一个空数组var result = [];// 不断的从拆分的数组中取元素进行比较,直到其中一边没有元素为止while(left.length > 0 && right.length > 0) {// 对拆分后的数组元素进行比较,小的放左边,大的放右边if(left[0] <= right[0]) {result.push(left.shift());} else {result.push(right.shift());}}// 将剩余的数组元素添加到结果数组(因为比较完以后有可能左边会有剩余元素或者右边会有剩余元素)return result.concat(left, right); }
 
-  
Array.slice() 与 Array.splice() 的区别
-  slice()方法返回一个新数组,包含从原数组中指定的开始位置到结束位置(不包括结束位置)的元素,不会修改原数组。数组的截取(不包含结束位置),返回新数组,不会修改原数组 
-  splice()方法通过删除或替换现有元素或者添加新元素来修改原数组。它会返回被删除的元素组成的数组。删除或替换修改原数组,会返回被删除的元素组成的数组 
数组中的Map和forEach的区别
-  相同点: -  Map和forEach都是循环遍历数组中的的每一项 
-  每次执行匿名函数都支持3个参数 (item,index,原数组) 
-  匿名函数中的this都是指向window的 
 
-  
-  区别: -  map有返回值,有映射的效果,返回一个新的数组,不改变原数组。适用于需要生成新数组,且新数组的元素是对原数组进行某种转换的情况,比如对数组中的每个元素进行计算并返回一个新数组 
-  forEach没有返回值return是不起作用的,不改变原数组,只用来遍历。适用于需要遍历数组但不需要生成新数组的情况,比如在循环中执行一些操作。 -  终止forEach可以使用try-catch抛出异常并结束循环 
 
-  
 
-  
for...in 和 for...of的区别
-  for...in:可以用来遍历数组、对象等可迭代对象。 -  遍历数组的话,输出的是数组元素的下标; 
-  遍历对象的话,输出的是对象的键 
 // 数组 const arr = ['a','b','c']for(let i in arr){console.log(i); }  // 对象 const obj = { a: 1, b: 2, c: 3 }for (let i in obj) {console.log(i); // 输出键名console.log(obj[i]); // 输出键值 }
-  
-  for...of:ES6引进的新特性。只能遍历数组,输出的是数组的元素 -  不能遍历对象,因为没有interator接口 
 // 数组 const arr = ['a','b','c'] for(let n of arr){console.log(n); }
-  
-  循环数组嵌套对象 const arrObj = [{ id: 1, name: '张三' },{ id: 2, name: '李四' },{ id: 3, name: '王五' }]for (let nObj of arrObj) {for (let n in nObj){console.log(nObj[n]); // 输出每个对象的键值} }
字符串常用方法
-  length:返回字符串的长度。const str = "Hello"; console.log(str.length); // 5
-  charAt(index):返回指定索引位置的字符。const str = "Hello"; console.log(str.charAt(1)); // e
-  concat(string1, string2, ...):将多个字符串连接起来。const str1 = "Hello"; const str2 = " World"; console.log(str1.concat(str2)); // Hello World
-  toUpperCase():将字符串转换为大写。const str = "Hello"; console.log(str.toUpperCase()); // HELLO
-  toLowerCase():将字符串转换为小写。const str = "Hello"; console.log(str.toLowerCase()); // hello
-  substring(startIndex, endIndex):提取从startIndex到endIndex(不包括)之间的子字符串。const str = "Hello World"; console.log(str.substring(6, 11)); // World
-  indexOf(substring, startIndex):返回指定子字符串第一次出现的索引位置。如果找不到,则返回 -1。const str = "Hello World"; console.log(str.indexOf("o")); // 4 console.log(str.indexOf("z")); // -1
-  replace(oldValue, newValue):将字符串中的指定值替换为新值,只替换第一个匹配项。const str = "Hello World"; console.log(str.replace("World", "Universe")); // Hello Universe
-  split(separator):将字符串分割为子字符串数组,使用separator参数作为分隔符。const str = "Hello,World,Universe"; console.log(str.split(",")); // ["Hello", "World", "Universe"]
-  trim():去除字符串两端的空格。const str = " Hello "; console.log(str.trim()); // Hello
-  startsWith(searchString, position):判断字符串是否以指定的内容开头。可选的position参数指定从哪个索引位置开始进行匹配。const str = "Hello World"; console.log(str.startsWith("Hello")); // true console.log(str.startsWith("World")); // false
-  endsWith(searchString, position):判断字符串是否以指定的内容结尾。可选的position参数指定从哪个索引位置结束进行匹配。const str = "Hello World"; console.log(str.endsWith("World")); // true console.log(str.endsWith("Hello")); // false
-  includes(searchString, position):判断字符串中是否包含指定的内容。可选的position参数指定从哪个索引位置开始进行匹配。const str = "Hello World"; console.log(str.includes("Hello")); // true console.log(str.includes("Universe")); // false
-  slice(startIndex, endIndex):提取从startIndex到endIndex(不包括)之间的子字符串。const str = "Hello World"; console.log(str.slice(6, 11)); // World
-  padStart(targetLength, padString):在字符串的开头添加指定的字符,直到字符串达到指定的长度。const str = "Hello"; console.log(str.padStart(10, "X")); // XXXXHello
-  padEnd(targetLength, padString):在字符串的末尾添加指定的字符,直到字符串达到指定的长度。const str = "Hello"; console.log(str.padEnd(10, "X")); // HelloXXXX
-  repeat(count):将字符串重复指定的次数。const str = "Hello"; console.log(str.repeat(3)); // HelloHelloHello
null和undefined
console.log(typeof null) // object 表示为“无”对象0
console.log(typeof undefined) // undefined 表示“无”的原始值 NaN(1)undefined
-  已经声明,未赋值 let o; console.log(o)
-  对象某个属性不存在 let obj = {} console.log(obj.a)
-  函数调用,少传一个参数 function fn(a,b){console.log(a,b) } fn(4)
-  函数的默认返回值(就是函数没有返回值的时候) function demo(){console.log("11") } console.log(demo())
(2)null
-  手动释放内存 let obj = {} obj = null
-  作为函数的参数(此参数不是对象) 
-  原型链的顶端 
console.log(typeof null); // object
console.log(typeof undefined); // undefined
console.log((null == undefined)); // true
console.log((null === undefined)); // false区别:
-  undefined是应该有值,但是没有赋值;null表示一个空值 
-  使用typeof判断类型的时候,undefined是undefined;null是object 
null是对象吗?
-  null不是对象 
-  但是typeof null会输出“object”类型,但这是JS存在的一个bug,最初使用32位系统的时候为了性能考虑,使用的是低位存储变量的类型信息,000开头代表是对象,null表示全零,所以会误判为object。