3.4
- 不能给基本类型的值添加属性
但是
var a=new String('ddd')
a.name='lee'
console.log(a.name)//'lee'
- 从一个变量向另一个变量复制基本类型值时,两个变量的任何操作不会相互影响,而如果从一个变量向另一个变量复制引用类型值时(包括数组),改变一个变量,会影响另一个变量
解决方法:对象克隆:
var clone = function(myObj){
if(typeof(myObj) != 'object') return myObj;
if(myObj == null) return myObj;
var myNewObj = new Object();
for(var i in myObj){
myNewObj[i] = clone(myObj[i]);
}
return myNewObj;
};
//这个更严谨
function clone(Obj) {
var buf;
if (Obj instanceof Array) {
buf=Array.prototype.slice.call(Obj)
return buf;
} else if (Obj instanceof Object){
buf = {}; // 创建一个空对象
for (var k in Obj) { // 为这个对象添加新的属性
buf[k] = clone(Obj[k]);
}
return buf;
}else{
return Obj;
}
}
//数组:
Array.prototype.clone=function(){
return this.slice(0);
}
- 判断对象是否为空
var isEmptyObj=function(obj){
for(var name in obj){
return false
}
return true
};//判断对象是否为空
- 传递参数只能按值传递,即使这个对象是按值传递,也会按引用来访问同一个对象
function setName(obj){
obj.name='nicholas'
obj=new Object()//引用的是一个局部对象,这在函数执行完毕后立即销毁
obj.name='greg'
}
var person=new Object()
setName()
alert(person.name)//'nicholas'
执行环境及作用域
作用域的前端,始终都是当前执行的代码所在环境的变量对象。如果这个环境是函数,则将其活动对象作为变量对象。标识符解析是沿着作用域链一级一级的向上搜索标识符的过程。延长作用域链
try-catch语句的catch块
with语句没有块级作用域
垃圾收集
- 标记清除
- 引用计数
object类型
var person={
'name':'lelele'
}
var proname='name'
console.log(person[proname])//不能用person.proname
- Array类型
var colors=new Array()
var colors=[]
var colors=Array()//可以是数字,也可以是数据项
检测数组:
typeof []; // "object"
[] instanceof Array; // true
typeof [] == "object" && [].constructor == Array;
Object.prototype.toString.call(arr) === "[object Array]";
转换方法
var colors=[1,2,3]
colors.toString()//'1,2,3'
colors.valueOf()//'1,2,3'
colors//'1,2,3'
队列方法:
var color=['red','blue']
var count=color.push('yellow')//2返回长度
var item=color.pop()//‘yellow’返回数据项
同理如unshift和shift
排序:
var values=[0,1,5,10,15]
values.reverse()//5,4,3,2,1颠倒位置不比大小
values.sort()//0,1,10,15,5
function compare(){
if(value1<value2){
return -1
}else if(value1>value2){
return 1
}else{
return 0
}
}
values.sort(compare)
操作方法:
concat
splice
slice
indexOf()比较是===
var person={name:'nicholas'}
var people=[{name:'nicholas'}]
people.indexOf(person)//-1
every每一项为true,则返回true
filter返回true的项组成数组
forEach对每一项执行函数,没有返回值
map()对每一项执行函数,返回每次函数调用的结果
some()数组中任意一项返回true都会返回true
reduce(function(prev,cur,index,array){}[,初始值])
reduceRight同理
- Date类型
var dat=new Date(this.date);
dat.setDate(1);
dat.setDate(dat.getDate()-dat.getDay());
for(var i=0;i<42;i++){
var single=$('span').eq(i+7);
single.html(dat.getDate());
if(dat.getMonth()!==this.date.getMonth()){
single.css({color:'lightgray'});
}else if(dat.getDate()===this.date.getDate()){
this.currentDate=single;//保存当前日期
single.css({color:'#fff',background:'#c81b01'});
}else if(dat.getDay()===0||dat.getDay()===6){
single.css({color:'#c81b01'});
}else{
single.css({color:'black'});
}
dat.setDate(dat.getDate()+1);
}
- Function类型
function sum(num1,num2){
return num1+num2
}
alert(sum(10,10))//20
var anotherSum=sum
alert(anotherSum(10,10))//20
sum=null
alert(anotherSum(10,10))//20
function outer(){
inner()
}
function inner(){
alert(arguments.callee.caller)//严格模式下运行会导致错误
}
outer()
Array.prototype.slice.call(arguments)//转换成数组
call,apply,bind的区别
- 基本包装类型
字符串:
var s1='some text'
var s2=s1.substring(2)
alert(s1)//不会变
var obj=new Object('some text')
alert(obj instanceof String)//true
var value='25'
var number=Number(value)
alert(typeof number)
var obj=new Number(value)
alert(typeof obj)
alert(obj instanceof Number)//true
- Boolean类型
var falseObject=new Boolean(false)//就是对象
var result=falseObject&&true
alert(result)//true
var falseValue=false;
result =falseValue&&true
alert(result//false)
- Number类型
var num=10
num.toString(16)//'a'
var num=10.005
num.toFixed(2)//10.01
var num=10.004
num.toFixed(2)//10.00
var num=10
num.toExponential(1)//1.0e+1
var num=100
num.toPrecision(1)//1e+2
num.toPrecision(2)//99
num.toPrecision(3)//99.0
var numberObject=new Number(10)
var numberValue=10
alert(typeof numberObject)//'object'
alert(typeof numberValue)//'number'
alert(numberObject instanceof Number)//true
alert(numberValue instanceof Number)//false
- String
concat('','')
slice()
substring()//参数为负转换成0
substr(m,n(返回的个数))
trim()
function trim(str){ //删除左右两端的空格
return str.replace(/(^\s*)|(\s*$)/g, "");
}
function ltrim(str){ //删除左边的空格
return str.replace(/(^\s*)/g,"");
}
function rtrim(str){ //删除右边的空格
return str.replace(/(\s*$)/g,"");
}
eval()
eval(‘function sayHi(){alert(‘hi’)}’)
不存在变量提升
在严格模式下,外部访问不到eval()创建的任何变量或函数
- Math方法
Math.max(3,5,32,65)
Math.min()
Math.ceil()
Math.round()
Math.floor()
Math.random()//[0,1)
return Math.random()<.5?1:-1;
- 理解对象
var person={}
Object.defineProperty(person,'some',{
writable:false,
value:'nick'
})
var person={
name:'ddd'
}
Object.defineProperty(person,'sex',{
get:function(){
return this.name
},
set:function(val){
this.name=val
}
})
创建对象
- 工厂模式
function createPerson(name,age,job){
var o=new Object()
o.name=name
o.age=age
o.job=job
o.sayName=function(){
alert(this.name)
}
return o
}
var person1=createPerson('nik',29,'doctor')
person1.sayName()
- 构造函数模式
function Person(name,age,job){
this.name=name
this.age=age
this.job=job
this.sayName=function(){
alert(this.name)
}
}
var person1=new Person('nik',29,'doctor')
person1.sayName()
- 原型模式
function Person(){
}
Person.prototype.name='le'
Person.prototype.sayName=function(){
alert(this.name)
}
var person=new Person()
person.sayName()
hasOwnProperty()判断是否存在于实例
function hasPrototypeProperty(object,name){
return (!object.hasOwnProperty(name))&&(name in object)
}
//关于in
function Person(){
}
Person.prototype.name='nick'
Person.prototype.age=30
Person.prototype.job='doctor'
var keys=Object.keys(Person.prototype)
console.log(keys)//['name','age','job']
var p=new Person()
var m=Object.keys(p)
console.log(m)//[]
p.name='yy'
p.age=29
var n=Object.keys(p)
console.log(n)//['name','age']
for(var i in p){
console.log(i)//name age job
}
function Person(){
}
var friend=new Person()//实例指向原型,而这里重写了原型
Person.prototype={
constructor:Person,
sayName:function(){
alert('ddd')
}
}
friend.sayName()
- 组合使用构造函数和原型模式
function Person(name,age,job){
this.name=name;
this.age=age
this.job=job
}
Person.prototype={
constructor:Person,
sayName:function(){
alert(this.name)
}
}
var person=new Person('ddd',55,'doctor')
- 动态原型模式
function Person(name,age,job){
this.name=name
this.age=age
this.job=job
if(typeof this.sayName!='function'){
Person.prototype.sayName=function(){
alert(this.name)
}
}
}
var person=new Person('dd',55,'dd')
person.sayName()
- 寄生构造函数模式
function Person(name,age,job){
var o=new Object()
o.name=name;
o.age=age
o.job=job
o.sayName=function(){
alert(this.name)
}
return o
}
var friend = new Person('nick',55,'engineer')
friend.sayName()
- 稳妥构造函数模式
function person(name,age,job){
var o new Object
o.sayName=function(){
alert(name)
}
return o
}
var friend=Person('nock',29,'ddd')
friend.sayName()
继承:
- 原型链
function SuperType(){
this.property=true
}
SuperType.prototype.getSuperValue=function(){
return this.property
}
function SubType(){
this.subproperty=false
}
SubType.prototype=new SuperType()
SubType.prototype.getSubValue=function(){
return this.subproperty
}
var instance=new SubType()
alert(instance.getSuperValue())
alert(Object.prototype.isPrototypeOf(instance))//true
alert(SubType.prototype.isPrototypeOf(instance))//true
alert(SuperType.prototype.isPrototypeOf(instance))//true
- 借用构造函数
function SuperType(){
this.colors=['red','blue','green']
}
function SubType(){
SuperType.call(this)//实例
}
var instance=new SubType()
var instance2=new SubType()
instance.colors.push('black')
console.log(instance2.colors)//['red','blue','green']
- 组合继承
会调用两次超类
function SuperType(name){
this.colors=['red','blue','green']
this.name=name
}
SuperType.prototype.sayName=function(){
alert(this.name)
}
function SubType(name,age){
SuperType.call(this,name)//实例
this.age=age
}
SubType.prototype=new SuperType()
SubType.prototype.constructor=SubType
- 原型式继承
function object(o){
function F(){}
F.prototype=o
return new F()
}
//都会共享,相当于Object.create()
- 寄生式继承
function createAnother(original){
var clone=object(original)
clone.sayHi=function(){
alert('hi')
}
return clone
}
- 寄生组合式继承
function inheritProperty(subType,superType){
var prototype=object(superType.prototype)
prototype.constructor=subType
subType.prototype=prototype
}
function SuperType(name){
this.name=name
this.colors=['red','blue','green']
}
SuperType.prototype.sayName=function(){
alert(this.name)
}
function SubType(name,age){
SuperType.call(this,name)
this.age=age
}
inheritProperty(SubType,SuperType)
SubType.prototype.sayAge=function(){
alert(this.age)
}
var per=new SubType('lll',29)
per.sayName()