一,函数对象
所有引用类型(函数,数组,对象)都拥有__proto__属性(隐式原型)
所有函数拥有prototype属性(显式原型)(仅限函数)
原型对象:拥有prototype属性的对象,在定义函数时就被创建
二、构造函数
//创建构造函数
function Word(words){
this.words = words;
}
Word.prototype = {
alert(){
alert(this.words);
}
}
//创建实例
var w = new Word("hello world");
w.print = function(){
console.log(this.words);
console.log(this); //Person对象
}
w.print(); //hello world
w.alert(); //hello world
当调用某种方法或查找某种属性时,首先会在自身调用和查找,如果自身并没有该属性或方法,则会去它的__proto__属性中调用查找,也就是它构造函数的prototype中调用查找
三、原型
①所有引用类型都有一个__proto__(隐式原型)属性,属性值是一个普通的对象
②所有函数都有一个prototype(原型)属性,属性值是一个普通的对象
③所有引用类型的__proto__属性指向它构造函数的prototype
var a = [1,2,3];
a.__proto__ === Array.prototype; // true
四、原型链
当访问一个对象的某个属性时,会先在这个对象本身属性上查找,如果没有找到,则会去它的__proto__隐式原型上查找,即它的构造函数的prototype,如果还没有找到就会再在构造函数的prototype的__proto__中查找,这样一层一层向上查找就会形成一个链式结构,我们称为原型链。
举例,有以下代码
function Parent(month){
this.month = month;
}
var child = new Parent('Ann');
console.log(child.month); // Ann
console.log(child.father); // undefined
五、构造函数、对象实例、原型对象三者之间的关系
1.构造函数可以实例化对象
2.构造函数中有一个属性叫prototype,是构造函数的原型对象
3.构造函数的原型对象(prototype)中有一个constructor构造器,这个构造器指向的就是自己所在的原型对象所在的构造函数
4. 实例对象的原型对象(proto)指向的是该构造函数的原型对象
5.构造函数的原型对象(prototype)中的方法是可以被实例对象直接访问的
- 当访问一个对象的属性(包括方法)时,首先查找这个对象自身有没有该属性
- 如果没有就查找它的原型(也就是 __proto__指向的 prototype 原型对象)
- 如果还没有就查找原型对象的原型(Object的原型对象)
- 依此类推一直找到 Object 为止(null)
- __proto__对象原型的意义就在于为对象成员查找机制提供一个方向,或者说一条路线
六、类class
class Dog():
""" very first try """
def __init__(self, name, age,):
"""initiate name and age"""
self.name = name
self.age = age
def sit(self):
print(self.name.title() + " is now sitting")
def roll_over(self):
print(self.name.title() + " rolled over!")
首字母大写名称指的是类,其中Dog()中的()是空的,因为是从空白创建这个类 类中的函数称为 方法,
对于__init__(特定),开头结尾各俩下划线,每次根据Dog创造新的实例的时候就会自动运行 其中定义的三个实参,self, name
,age。 self是必不可少且必须位于最前的。 当调用__init__创建Dog实例时,将自动传入实参self,不需要传递值。
每个与类相关联的方法调用都自动传递实参self,是指向实例本身的引用
以self为前缀的变量可以供类中的所有方法使用,可以通过类的任何实例来访问变量。 self.name = name
获取存储在形参name中的值,并将其存储在变量name中,然后该变量name被关联到当前创建的实例中。
可以通过实例访问的变量(name,age)称为属性。
根据类创建实例
class Dog()后
my_dog = Dog('Lucas', 6)
print("my dog's name is " + my_dog.name + ".")
print("my dog is " + str(my_dog.age) + ".")
当传递实参时,调用了Dog类中的方法__init__(),方法__init__创建了一个表示特定小狗的示例。方法__init__并未显式包含return语句,但自动返回一个表示这条狗的实例。利用变量my_dog储存这个实例。
首字母大写的名称Dog表示类
小写的名称my_dog指的是根据类创建的实例
访问属性用句点表示法即可,my_dog.name
默认值
类中的每个属性都必须有初始值,哪怕这个值是0或者空字符串。在方法__init__()内指定这种初始值时,无需包含为它提供初始值的形参。
class Car:
def __init__(self, make, model, year):
self.make = make
self.model = model
self.year = year
self.odometer = 0
def descriptive_name(self):
long_name = str(self.year) + ' ' + self.make + ' ' + self.model
return long_name.title()
def miles(self):
print('this car has ' + str(self.odometer) + " miles on it. ")
my_new_car = Car('audi', 'a4', 2016)
print(my_new_car.descriptive_name())
my_new_car.miles()
>
>2016 Audi A4
this car has 0 miles on it.
继承
创建子类时,最首先的任务是给父类所有属性赋值。子类的方法__init__需要父类施以援手?????
电动汽车属于汽车,故以电动汽车作为子类,这样就只需为电动汽车特有的属性和行为编码。
class Car:
def __init__(self, make, model, year):
self.make = make
self.model = model
self.year = year
self.odometer = 0
def descriptive_name(self):
long_name = str(self.year) + ' ' + self.make + ' ' + self.model
return long_name.title()
def update_odometer(self, mileage):
"""set the reading to referred value"""
self.odometer = mileage
def miles(self):
print('this car has ' + str(self.odometer) + " miles on it. ")
class ElectricCar(Car):
def __init__(self, make, model, year):
“”“初始化父类的属性”“”
super().__init__(make, model, year)
my_tesla = ElectricCar('tesla', 'model s', 2016)
print(my_tesla.descriptive_name())
注意:
1.创建子类时,父类必须包含在当前文件中,且位于子类前面。
2.定义子类时,必须在括号内指定父类的名称,方法__init__必须接受创建Car实例所需的信息
class ElectricCar(Car):
3.super()是一个特殊函数,将父类和子类联系起来
super().__init__(make, model, year)
这行代码调用父类方法__init__(),让Electricity实例包含父类的所有属性
4.
class ElectricCar(Car):
def __init__(self, make, model, year):
“”“初始化父类的属性”“”
super().__init__(make, model, year)
my_tesla = ElectricCar('tesla', 'model s', 2016)
创建一个E car的实例,并将其储存在变量my_tesla中,调用E Car类中定义的方法__init__(),init()可调用Car中定义的方法__init__()
七、JavaScript 中常见的几种数据类型:
基本类型:string,number,boolean
特殊类型:undefined,null
引用类型:Object,Function,Function,Array,Date,…
typeof
typeof 返回一个表示数据类型的字符串,返回结果包括:number、boolean、string、object、undefined、function等6种数据类型。如果是判断一个基本的类型用typeof就是可以的。
typeof ''; // string 有效
typeof 1; // number 有效
typeof true; //boolean 有效
typeof undefined; //undefined 有效
typeof null; //object 无效
typeof [] ; //object 无效
typeof new Function(); // function 有效
typeof new Date(); //object 无效
typeof new RegExp(); //object 无效
typeof 可以对JS基础数据类型做出准确的判断,而对于引用类型返回的基本上都是object, 其实返回object也没有错,因为所有对象的原型链最终都指向了Object,Object是所有对象的祖宗
。 如果判断的是引用类型的话,typeof 就显得有些力不从心了。
instanceof
instanceof 是用来判断 A 是否为 B 的实例对,表达式为:A instanceof B,如果A是B的实例,则返回true,否则返回false。 在这里需要特别注意的是:instanceof检测的是原型,
[] instanceof Array; //true
{} instanceof Object;//true
new Date() instanceof Date;//true
Object.prototype.toString
toString是Object原型对象上的一个方法,该方法默认返回其调用者的具体类型,更严格的讲,是 toString运行时this指向的对象类型, 返回的类型格式为[object,xxx],xxx是具体的数据类型,其中包括:String,Number,Boolean,Undefined,Null,Function,Date,Array,RegExp,Error,HTMLDocument,… 基本上所有对象的类型都可以通过这个方法获取到。
Object.prototype.toString.call('') ; // [object String]
Object.prototype.toString.call(1) ; // [object Number]
Object.prototype.toString.call(true) ; // [object Boolean]
Object.prototype.toString.call(undefined) ; // [object Undefined]
Object.prototype.toString.call(null) ; // [object Null]
Object.prototype.toString.call(new Function()) ; // [object Function]
Object.prototype.toString.call(new Date()) ; // [object Date]
Object.prototype.toString.call([]) ; // [object Array]
Object.prototype.toString.call(new RegExp()) ; // [object RegExp]
Object.prototype.toString.call(new Error()) ; // [object Error]