10.10.JS-数组,类数组

231 阅读3分钟

1. 数组

  • 数组的定义
    • new Array(length/content);
      • var arr = new Array(1,2,3); // 内容为[1,2,3]的数组
      • var arr = new Array(10); // 长度为10的数组
    • 字面量
      • var arr = [1,2,3,,4];
  • 数组的读和写
    • arr[num]; // 不可以溢出读
    • arr[num] = 'xxx'; // 可以溢出写

2. 数组常用的方法

  • 改变原数组
    • push,pop,shift,unshift,sort,reverse
    • splice
  • 不改变原数组
    • concat,join -> split,toString,slice

2.1 数组push

Array.prototype.push = function () {
  for (var i = 0; i < arguments.length; i++) {
    this[this.length] = arguments[i];
  }
  return this.length;
}

2.2. pop

Array.prototype.pop = function () {
  var num = this[this.length - 1];
  this.length--;
  return num;
};

2.3. shift

Array.prototype.shift = function () {
  var num = this[0];
  for (var i = 1; i < this.length; i++) {
    this[i - 1] = this[i];
  }
  this.length--;
  return num;
};

2.4. unshift

// es6语法
Array.prototype.unshift = function () {
  var unshiftArr = [...arguments, ...this];
  this.length = unshiftArr.length;
  for (var i = 0; i < unshiftArr.length; i++) {
    this[i] = unshiftArr[i];
  }
  return unshiftArr.length;
};
// eval
Array.prototype.unshift = function () {
  var str = "";
  for (var i = 0; i < arguments.length; i++) {
    if (typeof arguments[i] == "string") {
      str += "'" + arguments[i] + "',";
    } else {
      str += arguments[i] + ",";
    }
  }
  for (var i = 0; i < this.length; i++) {
    if (typeof this[i] == "string") {
      str += "'" + this[i] + "',"
    } else {
      str += this[i] + ","
    }
  }
  var ary = eval("[" + str + "]");
  this.length = ary.length;
  for (var i = 0; i < ary.length; i++) {
    this[i] = ary[i];
  }
  return ary.length;
};
// concat
Array.prototype.unshift = function () {
  var arg = [];
  for (var i = 0; i < arguments.length; i++) {
    arg[i] = arguments[i];
  }
  arg = arg.concat(this);
  for (var i = 0; i < arg.length; i++) {
    this[i] = arg[i];
  }
  return this.length;
}

2.5 splice

arr.splice(从第几位开始,截取多少的长度,在切口处添加新的数据)

2.6. slice,join

var arr = [1,2,3,4,5];
// arr.slice(从该位开始截取,截取到该位)
var newArr = arr.slice(1,2);
// split() -- string方法
var str = arr.join(',')
var arr2 = str.split(',')
// string方法split和数组方法join配合使用

3. 排序

var arr = [1, 2, 3, 2, 8, 23, 5, 1];
// arr.splice(从第几位开始,截取多少的长度,在切口处添加新的数据)
// 1. 必须写俩形参
// 2. 看返回值   
//   1)当返回值为负数时,那么前面的数放在前面
//   2)为正数,那么后面的数在前
//   3)为0,不动
arr.sort(function (a, b) {
  // 具体
  // if (a > b) {
  //   return 1;
  // } else {
  //   return -1;
  // }
  return a - b; // 升序
  // return b - a; // 降序
})
// 乱序
arr.sort(function (a, b) {
  return Math.random() - 0.5;
})

var arr2 = ['221', '混合22', '扣扣333'];
function retBytes(str) {
  var num = str.length;
  for (var i = 0; i < str.length; i++) {
    if (str.charCodeAt(i) > 255) {
      num++;
    }
  }
  return num;
}
arr2.sort(function(a,b){
  return retBytes(a) - retBytes(b); // 字节长度升序
})

4. 类数组

  1. 可以利用属性名模拟数组的特性
  2. 可以动态增长length属性
  3. 如果强行让类数组调用push方法,则会根据length属性值得位置进行属性的扩充
// 类数组 含有length属性的对象
var obj = {
  "0": "a",
  "1": "b",
  "2": "c",
  length: 3,
  push: Array.prototype.push
}

5. 三目运算符

  • 形式:判断语句 ? 若为真,执行并返回结果 : 若为假,执行,并返回结果 ;
  • 三目运算符其实就是简化版的if(){...}else{...}语句

6. 封装type方法,判读数据类型

// 1. 把例外排除 null function
// 2. 分两类 原始值 引用值
// 3. 区分引用值 Object.prototype.toString
function type(target) {
  var template = {
    "[object Array]": "array",
    "[object Object]": "object",
    "[object Number]": "number - object",
    "[object Boolean]": "boolean - object",
    "[object String]": "string - object"
  }
  if (target == null) {
    return null;
  }
  if (typeof (target) == 'function') {
    return 'function';
  } else if (typeof (target) == 'object') {
    var str = Object.prototype.toString.call(target);
    return template[str];
  } else {
    return typeof (target);
  }
}
  • 优化type方法
function type(target) {
  var ret = typeof(target);
  var template = {
    "[object Array]": "array",
    "[object Object]": "object",
    "[object Number]": "number - object",
    "[object Boolean]": "boolean - object",
    "[object String]": "string - object"
  }
  if (target == null) {
    return null;
  } else if (ret == 'object') {
    var str = Object.prototype.toString.call(target);
    return template[str];
  } else {
    return ret;
  }
}

7. 数组去重,通过对象key-value属性

// var obj = {
//   1: "abc",
//   2: "abc"
// }
// obj[0] --> undefined;
// obj[1] --> 'abc';
// obj[2] --> undefined;
// 数组去重
Array.prototype.unique = function () {
  var temp = {},
    arr = [],
    len = this.length;
  for (var i = 0; i < len; i++) {
    if (!temp[this[i]]) {
      temp[this[i]] = this[i];
      arr.push(this[i]);
    }
  }
  return arr;
}

8. delete

  • 一旦经历了 var 的操作,所得出的属性,这种属性叫做不可配置的属性,这种属性 delete 不掉
  • 形参等同于 var
var b = (function (x) {
  delete x;
  return x; // x 为 1
})(1);

9. 函数表达式的函数名

var h = function a() {
  return 23;
}
// console.log(typeof a()); // 此时 a 无意义,此时只用 h 可以调用函数
console.log(typeof h()); // "number"

10. 日期转换成函数

function retDate(date) {
  var arr = ['一', '二', '三'];
  var ret = arr[date - 1];
  if (ret === undefined) {
    return 'error';
  } else {
    return ret;
  }
}