JavaScript高级程序设计(第3版)笔记(五)

来源:互联网 发布:富人国 知乎 编辑:程序博客网 时间:2024/05/01 18:31
第五章 引用类型    
     5.1  Object类型
           创建Object实例的两种方式
          (1)var person = new Object();  创建了object引用类型的一个实例,该实例保存在变量person中,使用的构造函数是Object
          (2)对象字面量表示法:
var person = {                name:'lily',                age:10}

                  或者  

var person = {};person.name = 'lily';person.age = 10;

           访问对象的属性一般使用点表示法,也可使用方括号表示
           
alert(person.name);alert(person['name']);
           注:当属性名中包含会导致语法错误的字符或者属性名使用的关键字或保留字,或者属性名为变量时,适用于方括号表示     
var propertyName = 'name';alert(person[propertyName]);person['first name'] = "lily"; //这种写法在中括号中允许,点表示法时会报错
           除必须情况,一般使用点表示法       
      5.2  Array类型   
            创建Array的方式:
           
var arr = new Array();var arr = new Array(20);//创建length为20的数组var arr = new Array("1","2","3"); // 创建内容为“1”,“2”,“3”的数组var arr = ['1','2','3']; //创建内容为“1”,“2”,“3”的数组var arr = [1,2,] // 创建2项或3项的数组,不要这样做,可能存在兼容性问题!!var arr = [,,];  //创建2项或3项的数组,不要这样做,可能存在兼容性问题!!var arr = [];    //创建一个空数组
           当索引大于数组的项数,为该索引对应的位置设置值时,数组的length+1,如果只是访问,不会改变 length。同时length不是只读的,可手动                  更改length的值,length变小,相应的项从后开始移除,length变大,对应项数的值默认为undefined       
var arr = ['1','2','3']; console.log(arr.length); //3arr[3] = "4";console.log(arr.length); // 4arr.length = 2;console.log(arr);        // ['1','2'];arr.length = 4;console.log(arr);        // ['1','2',undefined,undefined]

       注:索引数组与hash数组的区别
               hash数组:(稀疏数组)下标不连续的数组,可自定义下标的名称;原理:专门接收一个字符串,计算出一个尽量不重复的序号,相同字符                                    串,序号一样,然后将元素值保存在指定序号的位置length属性无效,遍历使用for(var key in arr){ var value = arr[key];}    
               索引数组:下标为数字的数组。
                                 length属性有效,遍历使用for(var i = 0; i < arr.length; i++){var value = arr[i]}
                hash数组查找速度快,不需要循环查找,只需通过对应属性名查找即可,与元素个数和存储位置无关,而索引数组需要遍历来进行查找,                    查找速度受元素个数和元素存储位置影响,查找速度可能会很慢

           1.Array.isArray(value); //判断对象value是否为Array;
              注:IE9+支持  
              所有对象都具有valueOf(),toString(),toLocaleString()方法,默认以逗号分隔的字符传格式返回数组项
           2.数组常用API
              数组转字符串:
               join将数组转换为字符串。arr.join()返回字符串,不改变原数组
               只能接受一个参数,arr.join(",")与arr.toString(),String(arr)相同。 
               arr.join("") //将数组无缝连接
               注:如果不给join传参,或者传undefined,数组将返回以","拼接的字符串,   
             
var arr = [1,2,3] arr.join(undefined);//"1,2,3"arr.join(null);     //"1null2null3"arr.join();         //"1,2,3"
              栈方法:(后进先出)
               arr.push(参数1,参数2); 
               push可以传入任意数量的参数,按顺序添加到数组的末尾,更改数组的长度,返回新数组
               arr.pop();//无参数
               pop,从数组的末尾除去数组的最后一项,改变数组长度,返回除去的最后一项
             队列方法:(先进先出)
               从前进从后出:arr.unshift(参数1,参数2) //可以传入任意数量的参数,返回新数组
                                      arr.pop()  
               从后进从前出:arr.push(参数1,参数2) 
                                      arr.shift() //返回除去的项,改变数组的长度
             重排序方法:
               reverse()按数组反序排列,改变数组,并返回新数组

               sort()升序排列,改变数组,并返回新数组。存在问题:默认将数组的每项通过toString()转化为字符串,通过unicode编码排序,是数字不能

               正确排序          

var arr = [1,3,2,4,12];arr.reverse(); // [12,4,2,3,1]arr.sort();    // [1,12,2,3,4] //sort解决方法:sort()中传入比较函数作为参数arr.sort(compare);function compare(value1,value2){     if(value1 > value2){            return 1;     }else if(value1 < value2){             return -1;      }else{             return 0;       }}alert(arr);      //[1,2,3,4,12] 
                    注:sort()方法根据比较函数的返回值进行排序。
                          若value1 < value2 ,在排序后的数组中value1应该排在value2的前面,返回值小于0
                          若value1 > value2 返回值大于0,

                   若value1 == value2,返回值为0

             连接截取:
               连接:var newArr = arr.concat(arr2);
                         首先会复制包含arr所有项的新数组,然后将arr2数组打散成每个项添加的新数组的后面返回
                         注:1.concat无权修改原数组,返回新数组,需要用新变量接住 
                                2.可以arr.concat(arr2,值1,值2,...),concat具有打散数组的功能
               截取:var newArr = arr.slice(starti,endi);
                         截取从starti坐标开始到endi之前的一个坐标之间的数组(含头不含尾)
                         注:1.slice也是无权修改原数组,需要新变量接收,省略第二个参数,截取到末尾
                                2.slice方法中的参数可以为负数(实际就是截取倒数第多少到倒数第多少),负数与length相加可以确定对应                                                                 的位置如长度为5的一个数组arr,arr.slice(-2,-1)与调用arr.slice(3,4)一样
                                3.如果结束位置小于起始位置返回空数组
             splice方法:删除,插入,替换
               删除:var deletes = arr.splice(starti,n);
                         删除arr中从starti开始的n个元素 ,返回一个由被删除的元素组成的临时数组
               插入:var deletes = arr.splice(starti,0,值1,值2,...);
                        原数组被修改,从数组的starti位置开始插入值1,值2,原starti位置及其后的值,向后顺移,由于为未删除元素,所以返回空数组
                        注:第二个参数0,代表插入,与cancat相比splice不支持打散数组,但是会修改原数组,splice中如果传入数组,数组会变成子

                               数组
               替换:var deletes = arr.splice(starti,n,值1,值2,...);
                         先删除从starti(包含starti)开始的n个项,然后从starti位置上开始插入值1,值2。
                         注:删除的个数与插入项的个数可以不一致
             位置方法:indexOf(),lastIndexOf()
               都接收两个参数,要查找的项和查找的起点位置索引(可选),indexOf()表示从头找,lastIndexOf()表示从末尾开始找,都返回第一次找                    到的项的坐标,没有返回-1;
               注:1.做全等比较(===)
                      2.IE9+支持
             迭代方法:
               每个方法都接收两个参数,一个为在每个项上运行的函数,一个是运行该函数作用域对象——影响this的值(可选),传入这些方法的函数                  会接收三个参数,数组项的值,项的索引,和对象本身
               every(),对数组中的每一项运行给定函数,函数对每一项都返回true,则返回true,无返回值,则返回false
               filter(), 对数组中的每一项运行给定函数,返回该函数会返回true的项组成的数组,无返回值,返回空数组
               forEach(),对数组中的每一项运行给定函数,无返回值
               map(),对数组中的每一项运行给定函数,返回函数对每一项返回的结果组成的数组,函数中无return(无返回值),返回undefined组成的数组
               some(),对数组中的每一项运行给定函数,函数对任意一项返回true,则返回true,无返回值,则返回false
               注:(1)不会修改原数组 
                      (2)支持IE9+
                      (3)虽然以上迭代方法不会修改原数组,但是5个方法可以通过以下形式修改原数组
                      

var arr = [1,2,3,4];var arr1 = arr.forEach(function(item,index,arr){           arr[index] = item * 2;})console.log(arr1)//undefined 无返回值console.log(arr) // [2,3,6,8]
                    
var arr = [1,2,3,4];var arr1 = arr.filter(function(item,index,arr){                arr[index] = item - 1;                return item > 1;})console.log(arr1); //2,3,4console.log(arr);  //[0,1,2,3]
                      (4)every方法在数组每一项执行函数时,只要出现返回为false,将直接返回false,数组接下来的项将不再执行函数
                               some方法与every类似,在数组每一项执行函数时,只要出现返回为true,将直接返回true,数组接下来的项将不再执行函数                      
var arr = [3,3,3]; var result = arr.some(function(item,index,arr){                  arr[index] = item + 1;                  return item > 2; })console.log(arr);    //[4,3,3]console.log(result); // true        
                        
var arr = [3,3,3];var result = arr.some(function(item,index,arr){                  arr[index] = item + 1;})console.log(arr);    //[4,4,4]console.log(result); // false
                      (5)不为数组中缺少的元素调用该回调函数
             缩小方法:

               reduce(),reduceRight(),都会迭代数组中的每一项,构建最终返回值,reduce从第一项开始遍历,reduceRight从最后一项开始遍历接收

               两个参数,一个为运行在每一项上的函数,一个为作为缩小的初始值(可选);为传入的函数提供4个参 数:前一个值,当前值,当前

               项的索引和数组对象,函数返回的值会作为下一次执行函数的第一个参数,第一次迭代发生在第二项上,函数一个参数为数组第一个项的值

      
var values = [1,2,3,4];values.reduce(function(pre,cur,index,arr){                     return pre + cur;}) //10var values = [1,2,3,4];values.reduce(function(pre,cur,index,arr){                    return pre + cur;},5) //15
               支持IE9+

   疑问:1.valueOf()与toString()的区别
                valueOf()与toString()一般不显式使用,而是js隐式转换,
                valueOf()返回最适合该对象类型的原始值;
                toString()将该对象的原始值以字符串的形式返回
                在数值运算中,会优先调用valueOf();字符运算中会优先调用toString();
                array的toString()方法返回以逗号分割的数组成员;
                function的toString()方法返回函数的文本定义 如:(function test(x){return x;}).toString()=>"function test(x){return x;}";
                RegExp的toString()方法也是返回文本定义     如:(/\d+/g).toString();=> '/\d+/g';
                Date的toString()方法会返回对应字符串形式   如:(new Date()).toString()=> "Sat Dec 02 201722:31:31 GMT+0800 (中国标准时间)"       
        
var colors = ['red','black','white'];Array.isArray(colors);             // trueArray.isArray(colors.toString());  // falseArray.isArray(colors.valueOf());   // truealert(colors);                //@1 red,black,whitealert(colors.toString()); //@2  red,black,whitealert(colors.valueOf()); // @3 red,black,white
                  @1,@2与@3返回之所以一样是因为alert方法的参数需要字符串格式的,所以在执行alert方法之前都会调用toString()方法,进行隐式转换
                  
var obj = {          a: 1,          valueOf: function(){ console.log("使用了valueOf");return this.a},          toString: function(){console.log("使用了toString");return this.a}}; obj+1; //使用了valueOf 2alert(obj); //使用了toString 1
                   注:toLocaleString()与以上不同的是,当数组调用toLocaleString()时,数组中的每一项也是调用toLocaleString()方法
                    
var a = {      i:2,      valueOf: function(){console.log("valueOf a");return this.i},      toString: function(){console.log("toString a");return this.i },      toLocaleString: function(){console.log("toLocaleString a");return this.i}             };var b = {                                 i:2,      valueOf: function(){console.log("valueOf b");return this.i},      toString: function(){console.log("toString b");return this.i },      toLocaleString: function(){console.log("toLocaleString b");return this.i}};var arr = [a,b];arr.valueOf()+1;  //toString a     toString b       "2,21"
                借鉴于:https://www.cnblogs.com/peakleo/p/6248242.html      
              2.arr.sort()数组排序
                (1)简单升序 比较函数:function compare(a,b){return a-b;}
                (2)简单降序 比较函数:function compare(a,b){return b-a;}
                (3)根据数组对象中的某个属性值如何排序            
var arr = [       {name:'a',age: 12},       {name:'b',age: 10},       {name:'c',age: 22}];function compare(property){         return function(a,b){         var value1 = a[property];                var value2 = b[property];                return value1 - value2;                }}console.log(arr.sort(compare));

                (4)自定义排序(升序)/*暂时没看懂*/ 

var InsertionSort = function InsertionSort(a, from, to) {                    for (var i = from + 1; i < to; i++) {                        var element = a[i];                                for (var j = i - 1; j >= from; j--) {                                var tmp = a[j];                                        var order = comparefn(tmp, element);                                        if (order > 0) {                                        a[j + 1] = tmp;                                        } else {                                                break;                                        }                                 }                                 a[j + 1] = element;                        }                    };
               (5)根据参数确定是升序还是降序                   
function compare(attr,rev){ //默认降序排列rev = rev ? 1 : -1;        return function(a,b){        return rev * (a[attr]-b[attr]);                }}var arr = [{name:'a',age: 12},        {name:'b',age: 10},        {name:'c',age: 22}];arr.sort(compare('age',false));

                借鉴于:https://segmentfault.com/a/1190000000410506

             3.为什么?              

var person = {name:"lily"}; var people = [{name:"lily"}];var morePeople = [person]people.indexOf(person) //-1;morePeople.indexOf(person) //0
                对象中保存的实际是存储数据的指针,对象间相等比较,实际是指针的比较,指针指向同一个位置,则两对象是相等的                
var obj = {name: "lily"};var obj1 =obj;var obj2 = {name: "lily"};obj1 == obj // true;  obj1 === obj // true;obj2 == obj  // false
                同理 虽然morePeople里的对象与people里的对象看起来是一样,但实际对象的指针指向是不同的
                morePeople中的对象引用的person的指针,指针相同所以morePeople.indexOf(person) //0,而people.indexOf(person) //-1;

阅读全文
0 0
原创粉丝点击