JSタイプ判定と深さコピー


JSタイプ判定と深さコピー
  • タイプ判断
  • JSデータタイプ
  • データタイプの判断
  • 深浅コピー
  • 浅いコピー
  • ディープコピー
  • 首層浅いコピー
  • 深さ優先、広さ優先
  • 巡回
    タイプ判定
    JSデータタイプ
  • 基本データタイプ:String、Number、Boolean、Symbol、Null、Unidefined
  • 参照データタイプ:Object
  • データタイプの判断
  • typeof
  • typeof 'aa'          // "string"
    typeof 1;			 // "number" 
    typeof true;	     // "boolean" 
    typeof Symbol();	 // "symbol" 
    typeof [];	         // "object" 
    typeof {};	         // "object" 
    typeof undefined; ;	  // "undefined" 
    typeof null;     	 // "object"
    typeof new Date();    // "object" 
    typeof new Function();    // "object" 
    typeof new RegExp();    // "object" 
    
    
    typeofがAray、null、Object、Date、Regを明確に区分できないことが見られます.
  • instance ofは、既知のオブジェクトであるtargetの具体的なタイプを判断し、AがBであるかどうかを判断し、検出されたのはプロトタイプ
  • である.
    [] instanceof Array  // true
    Symbol() instanceof Symbol  // true
    {} instanceof Object  // true
    new Date() instanceof Date  // true
    new RegExp() instanceof RegExp  // true
    new Function() instanceof Function  // true
    
  • constructor
  • [].constructor ===  Array  // true
    Symbol().constructor ===  Symbol  // true
    {} instanceof Object  // true
    new Date().constructor ===  Date  // true
    new RegExp().constructor ===  RegExp  // true
    new Function().constructor ===  Function  // true
    
  • prototype Object.prototype.toString.call====「[object Type]
  • Object.prototype.toString.call(1) ===  '[object Number]'
    Object.prototype.toString.call('') ===  '[object String]'
    Object.prototype.toString.call(true) ===  '[object Boolean]'
    Object.prototype.toString.call(null) ===  '[object Null]'
    Object.prototype.toString.call(undefined) ===  '[object Undefined]'
    Object.prototype.toString.call([]) ===  '[object Array]'
    Object.prototype.toString.call(new Date) ===  '[object Date]'
    Object.prototype.toString.call(function a(){}) ===  '[object Function]'
    
    
    配列の判断方法
    function adjustArray(o) {
        if(!o) {
            return false;
        }
        if(typeof Array.isArray === 'function') {
            return Array.isArray(o);
        } else {
            return Object.prototype.toString.call(o) === '[object Array]';
        }
    }
    
    濃淡コピー
    浅いコピー
    浅いコピーとは、参照だけをコピーして本物の値をコピーしないということです.を選択します
    コピー
  • 方法1,
  • //   
    export function deepCopy(target) {
        if(!target || typeOf target != 'object') {
            return target;
        }
        let newObj = target.constructor == Array ? [] : {};
        for (let i in target) {
            if(target.hasOwnProperty(i)){
                if(target[i] && typeof target[i] == 'object'){
                    newObj[i] = deepCopy(target[i]);
                } else {
                    newObj[i] = target[i];
                } 
            }
        }
        return newObj;
    }
    
    
  • 方法二
  • // JSON     (undefined、function、symbol           )
    let newObj = JSON.parse(JSON.stringfy(target));
    
    最初のレイヤーのコピー
    最初の層が浅いコピー:対象の第1の層を深くコピーし、後の部分が浅いコピーであることから、「最初の層が浅いコピー」と呼ぶことができる.
  • js配列には2つの方法のconcatとsliceがあり、元の配列のコピーを実現することができます.この2つの方法は、元の配列を変更することなく、修正された新しい配列を返します.彼らが実現したのは、最初の層の浅いコピー
  • です.
  • Object.assignのコピーは属性値です.最初のレイヤーの浅いコピーです.Object.assignメソッドは、ソースオブジェクト自体をコピーし、対象オブジェクトに列挙可能な属性のみを提供します.
  • 拡張演算子(…)は、同じようにオブジェクトに対して最初の層の浅いコピーを行う
  • である.
    //   
    const originArray = [1, 'aa',[ 'bb',2]];
    const originObj = {a:1,b:{bb:2}};
     
    const cloneArray = [...originArray];
    cloneArray[0] = 0;
    cloneArray[3].push(3);
    console.log(originArray); // [1, 'aa',[ 'bb',2, 3]];
     
    const cloneObj = {...originObj};
    cloneObj.a = 2;
    cloneObj.b.bb = 'rrr';
    console.log(originObj); // {a:1,b:{bb:'rrr'}}
    
    最初のレイヤーの浅いコピーの実現は、オブジェクトの最初のレイヤーを巡回します.
    function complexClone(source) {
      const targetObj = source.constructor === Array ? [] : {}; 
      for (let key in source) { //     
        if (source.hasOwnProperty(key)) {
          targetObj[key] = source[key];
        }
      }
      return targetObj;
    }
    
    let temp = [1,2,3, [4,5]];
    let cloneArr = complexClone(temp);
    cloneArr[3][0] = 'aaaaa';
    console.log(temp) // [1,2,3, ['aaaaa',5]];
    
    まとめ:赋値演算子=実現されるのは、浅いコピーであり、対象の参照値のみをコピーすることです.JavaScriptでは配列と対象が持参するコピー方法はすべて「最初の層が浅いコピー」です.JSON.strigifyは、深コピーを実現していますが、対象に対して要求があります.本当に深いコピーをしたいなら、再帰してください.
    深さ優先、広さ優先エルゴード
    木の遍歴と似ています.
  • 深さ優先エルゴード(DFS):サブノードを優先的に発見し、サブノードはトラバース完了後に兄弟ノードを巡回する.
  • 広さ優先エルゴード:同じレベルの兄弟ノードを優先的に遍歴し、すべての兄弟ノードを記録した後、再びサブノードを巡回する.
  • Advinced-Frontendには二つの解答内容がはっきりしていますので、深さ優先、広さ優先、深さ優先、深さ優先コピー優先、広さ優先コピー実現をお勧めします.