javascript学习--(四)面向对象:
一、生成器generator: javascript里的generator函数是用function*定义的, 案例:yield 也会返回 function* foo(x){ yield x+1; yield x+2; yield x+3; return x+4; };
斐波那契函数 不用生成器来写的函数: function fib(max){ var t, a=0, b=1, arr=[0,1]; while (arr.length<max){ [a,b]=[b,a+b] arr.push(b); } return arr; } fib(5); // [0, 1, 1, 2, 3] fib(10); // [0, 1, 1, 2, 3, 5, 8, 13, 21, 34] 用生成器函数 function*fib(max){ var t, a=0, b=1, n=0; while (n<max){ yield a; [a,b]=[b,a+b]; n++; } return; } 调用generator对象有两个方法, 一是不断地调用generator对象的next()方法: ext()方法会执行generator的代码,然后,每次遇到yield x; 就返回一个对象{value: x, done: true/false},然后“暂停”。 返回的value就是yield的返回值,done表示这个generator是否已经执行结束了。如果done为true, 则value就是return的返回值。 当执行到done为true时,这个generator对象就已经全部执行完毕,不要再继续调用next()了。 var f = fib(5); f.next(); // {value: 0, done: false} f.next(); // {value: 1, done: false} f.next(); // {value: 1, done: false} f.next(); // {value: 2, done: false} f.next(); // {value: 3, done: false} f.next(); // {value: undefined, done: true} 因为generator可以在执行过程中多次返回, 所以它看上去就像一个可以记住执行状态的函数 第二个方法是直接用for ... of循环迭代generator对象, 这种方式不需要我们自己判断done: for (var x of fib1(10)) { console.log(x); // 依次输出0, 1, 1, 2, 3, ... } 标准对象:Date、RegExp、JSON 在JavaScript的世界里,一切都是对象。 但是某些对象还是和其他对象不太一样。为了区分对象的类型,我们用typeof操作符获取对象的类型,它总是返回一个字符串: typeof 123; // 'number' typeof NaN; // 'number' typeof 'str'; // 'string' typeof true; // 'boolean' typeof undefined; // 'undefined' typeof Math.abs; // 'function' typeof null; // 'object' typeof []; // 'object' typeof {}; // 'object' 可见,number、string、boolean、function和undefined有别于其他类型。特别注意null的类型是object,Array的类型也是object,如果 我们用typeof将无法区分出null、Array和通常意义上的object——{}。 包装对象用new创建; var n = new Number(123); // 123,生成了新的包装类型 var b = new Boolean(true); // true,生成了新的包装类型 var s = new String('str'); // 'str',生成了新的包装类型
在JavaScript中,Date对象用来表示日期和时间。 var now = new Date(); now; // Wed Jun 24 2015 19:49:22 GMT+0800 (CST) now.getFullYear(); // 2015, 年份 now.getMonth(); // 5, 月份,注意月份范围是0~11,5表示六月 now.getDate(); // 24, 表示24号 now.getDay(); // 3, 表示星期三 now.getHours(); // 19, 24小时制 now.getMinutes(); // 49, 分钟 now.getSeconds(); // 22, 秒 now.getMilliseconds(); // 875, 毫秒数 now.getTime(); // 1435146562875, 以number形式表示的时间戳 JSON是JavaScript Object Notation的缩写,它是一种数据交换格式。 在JSON中,一共就这么几种数据类型: number:和JavaScript的number完全一致; boolean:就是JavaScript的true或false; string:就是JavaScript的string; null:就是JavaScript的null; array:就是JavaScript的Array表示方式——[]; object:就是JavaScript的{ ... }表示方式。 序列化 让我们先把小明这个对象序列化成JSON格式的字符串: 'use strict'; var xiaoming = { name: '小明', age: 14, gender: true, height: 1.65, grade: null, 'middle-school': '\"W3C\" Middle School', skills: ['JavaScript', 'Java', 'Python', 'Lisp'] }; var s = JSON.stringify(xiaoming, null, ' '); console.log(s); 结果: { "name": "小明", "age": 14, "gender": true, "height": 1.65, "grade": null, "middle-school": "\"W3C\" Middle School", "skills": [ "JavaScript", "Java", "Python", "Lisp" ] } 案例: 'use strict' var url = 'https://api.openweathermap.org/data/2.5/forecast?q=Beijing,cn&appid=800f49846586c3ba6e7052cfc89af16c'; $.getJSON(url, function (data) { var info = { city: data.city.name, weather: data.list[0].weather[0].main, time: data.list[0].dt_txt }; alert(JSON.stringify(info, null, ' ')); });
面向对象: 类:类是对象的类型模板,例如,定义Student类来表示学生, 类本身是一种类型,Student表示学生类型,但不表示任何具体的某个学生; 实例:实例是根据类创建的对象, 例如,根据Student类可以创建出xiaoming、xiaohong、xiaojun等多个实例,每个实例表示一个具体的学生,他们全都属于Student类型。 JavaScript不区分类和实例的概念, 而是通过原型(prototype)来实现面向对象编程 案例: var Student = { name: 'Robot', height: 1.2, run: function () { console.log(this.name + ' is running...'); } }; var xiaoming = { name: '小明' }; xiaoming.__proto__ = Student; 注意最后一行代码把xiaoming的原型指向了对象Student,看上去xiaoming仿佛是从Student继承下来的: xiaoming.name; // '小明' xiaoming.run(); // 小明 is running... xiaoming有自己的name属性,但并没有定义run()方法。不过,由于小明是从Student继承而来, 只要Student有run()方法,xiaoming也可以调用: JavaScript的原型链和Java的Class区别就在,它没有“Class”的概念,所有对象都是实例,所谓继承关系不过是把一个对象的原型指向另一个对象而已。 如果你把xiaoming的原型指向其他对象: var Bird = { fly: function () { console.log(this.name + ' is flying...'); } }; xiaoming.__proto__ = Bird; 现在xiaoming已经无法run()了,他已经变成了一只鸟: xiaoming.fly(); // 小明 is flying... 在JavaScrip代码运行时期,你可以把xiaoming从Student变成Bird,或者变成任何对象。 // 原型对象: var Student = { name: 'Robot', height: 1.2, run: function () { console.log(this.name + ' is running...'); } }; function createStudent(name) { // 基于Student原型创建一个新对象: var s = Object.create(Student); // 初始化新对象: s.name = name; return s; } var xiaoming = createStudent('小明'); xiaoming.run(); // 小明 is running... xiaoming.__proto__ === Student; // true
心有猛虎,细嗅蔷薇