《JavaScript高级程序设计》读书笔记-第五章(引用类型)

2019-06-19  本文已影响0人  极奏

引用类型

引用类型的值( 对象 )是引用类型的一个实例。在ECMAScript中,引用类型是一种数据结构,用于将数据和功能组织在一起。

引用类型有时候也被称为对象定义,因为它们描述的是一类对象所具有的属性和方式。

Object类型

创建Object实例的两种方式:
1、new操作符后跟着Object构造函数

var person = new Object()
persion.name = 'Nicholas'
person.age = 29

2、对象字面量表示法

var person = {
  name: 'Nicholas',
  age: 29
}
person['first name'] = 'Nicholas'  //方括号表示法
person.age = '18'                 //点表示法
Array类型

虽然ECMAScript数组与其他语言中的数组都是数据的有序列表,但与其他语言不同的是,ECMAScript数组的每一项都可以保存任何类型的数据而且ECMAScript数组的大小是可以动态调整的,即可以随着数据的添加自动增长以容纳新数据。

1、Array构造函数

var colors = new Array()
var colors = new Array(20)                       //length值为20的数组
var colors = new Array('red','blue','green')    //创建一个包含3个字符串值的数组

可以省略new操作符,结果相同

2、数组字面量表示法

var names = []
var colors = ['red','blue','yellow']
var colors = ['red','blue','green']
colors[colors.length] = 'black'
colors[colors.length] = 'brown'
检测数组

Array.isArray()方法

if( Array.isArray(value) ){
  //对象组执行某些操作
}

数组继承的toLocaleString()、toString()、和valueOf()方法,在默认情况下都会以逗号分隔的字符串的形式返回数组想。而如果使用join()方法

var colors =['red','blue','green']
console.log(colors.join(','))  //red,green,blue
console.log(colors.join('||')) //red||green||blue
栈方法

后进先出

进栈push()
出栈pop()

var colors = ['red','blue']
colors.push('brown')
colors[3] = 'black'
var item = colors.pop()  //'black'
队列方法

先进先出

入队shift()
出队push()

ECMAScript还为数组提供了unshift()方法。

重排序方法

正序sort()

逆序reverse()

操作方法

concat()

slice()

var colors = ['red','green','blue','yellow','pruple']
var colors2 = colors.slice(1)        //green,blue,yellow,purple
var colors3 = colors.slice(1,4)     //green,blue,yellow

splice()

splice()方法始终都会返回一个数组,该数组中包含从原始数组中删除的项,如果没有删除任何项,则返回一个空数组。

会修改原数组。

位置

indexOf()从开头找

lastIndexOf()从结尾往前找

这两个方法会使用全等操作符

迭代方法
var numbers = [1,2,3,4,5,4,3,2,1]

var everyResult = numbers.every(function(item,index,array)){
  return (item > 2)
}
console.log(everyResult)     //false
var numbers = [1,2,3,4,5,4,3,2,1]

var filterResult = numbers.filter(function(item,array,index){
  return (item > 2)
})

console.log(filterResult)    //[3,4,5,4,3]
var numbers = [1,2,3,4,5,4,3,2,1]

numbers.forEach(function(item,index,array)){
    //xxxxxxxxxxxxx
}
var numbers = [1,2,3,4,5,4,3,2,1]

var mapResult = numbers.map(function(item,index,array)){
  return item * 2
}
console.log(mapResult)  //[2,4,6,8,10,8,6,4,2]
var everyResult = numbers.some(function(item,index,array)){
  return (item > 2)
}
console.log(everyResult)     //true
缩小方法

reduce()
从数组的第一项开始,逐个遍历到最后
reduceRight()
从数组的最后一项开始,向前遍历到第一项

这个函数返回的任何值都会作为第一个参数自动传给下一项。
所以使用reduce()方法可以执行求数组中所有值之和的操作

var values = [1,2,3,4,5]
var sum = values.reduce(function(prev,cur,index,array){
  return prev + cur
})
console.log(sum)  //15
Date类型

ECMAScript中的Date类型是在早期Java中的java.util.Date类基础上构建的。为此,Date类型使用自UTC(Coordinated Universal Time,国际协调时间)1970年1月1日午夜(零时)开始经过的毫秒数来保存日期。

在使用这种数据存储格式的条件下,Date类型保存的日期能够精确到1970年1月1日之前或之后的285616年

要创建一个日期对象,使用new操作符和Date构造函数即可

var now = new Date()
RegExp类型

待更新

Function类型
函数声明与函数表达式
console.log(sum(10,10))
function sum(num1,num2){
  return num1 + num2
}

代码开始执行之前,解析器就已经通过一个名为函数声明提升(function declaration hoisting)的过程,读取并将函数声明添加到执行环境中。

如果改为函数表达式,就会报错

console.log(sum(10,10))
var sum = function(num1,num2){
  return num1 + num2
}
函数内部属性

函数内部有两个特殊的对象:argumentsthis

argument
function factorial(num){
  if(num <= 1){
    return 1
  } else {
    return num * factorial(num-1) 
  }
}

这个函数定义没有问题,问题在与这个函数执行与函数名factorial紧紧耦合在了一起,为了消除这种紧密耦合的现象,可以像下面这样使用arguments.callee

function factorial(num){
  if(num <= -1){
    return 1
  } else {
    return num * arguments.callee(num - 1)
  }
}
this

其行为和Java和C#中的this大致类似。换句话说,this引用的是函数以执行的环境对象

函数属性和方法
length
prototype

每个函数都包含两个非继承而来的方法 : apply()call()

apply:

function sum(num1 , num2){
  return num1 + num2
}

function applySum1(num1 , num2){
  return sum.apply(this, arguments)
}

function applySum2(num1 , num2){
  return sum.apply(this, arguments)
}

console.log(callSum1(10,10))  //20
console.log(callSum2(10,10))  //20

call:

function sum(num1 , num2){
  return num1 + num2
}
function callSum(num1 , num2){
  return sum.call(this, null1, num2)
}
window.color = 'red'
var object = {color : 'blue'}

function sayColor(){
  console.log(this.color)
}

sayColor()             //red

sayColor.call(this)    //red
sayColor.call(window)  //red
sayColor.call(object)  //blue

使用call()和apply()扩充作用域,最大的好处:就是对象不需要与方法有任何耦合关系。自己体会

window.color = 'red'
var object = { color: 'blue' }
function sayColor(){
  console.log(this.color)
}
var objectSayColor = sayColor.bind(object)
objectSayColor()                //blue

基本包装类型

为了便于操作基本类型值,ECMAScript还提供了了三个特殊的引用类型:BooleanNumberString

var s1 = 'some text'
var s2 = s1.substring(2)

等于

1、创建String类型的一个实例
2、在实例上调用指定的方法
3、销毁这个实例

var s1 = new String('some text')
var s2 = s1.substring(2)
s1 = null
var s1 = 'some text'
s1.color = 'red'
console.log(s1.color)  //undefined

Object构造函数也会像工厂方法一样,根据传入值的类型返回相应基本包装类型的实例

var obj = new Object('some text')
console.log(obj instanceof String)  //true
Boolean类型

Boolean类型的实例重写了valueOf()方法,返回基本类型值true或false,重写了toString()方法

布尔表达式中的所有对象都会被转换为true

var falseObject = new Boolean(false)
var result = falseObject && true
console.log(result)  //true

var falseValue = false
result = falseValue && true
console.log(resulet)  //false

typeof的表现方式

console.log( typeof falseValue )  //boolean
console.log( typeof falseObject )  //object
Number类型

Number同理

String类型
var string = 'hello world'
console.log(string.charAt(1))  //'e'
var string = 'hello world'
console.log(string.charCodeAt(1))  //'101'
var stringValue = 'hello'
var result = stringValue.concat('world')
console.log(result)       //'hello world'
console.log(stringValue)  //'hello'
var string = 'hello world'
console.log(string.slice(-3))    //'rld'
var string = 'hello world'
console.log(string.substr(3))     //'rld'
console.log(string.substr(3,-4))  //'空字符串'
var string = 'hello world'
console.log(string.substring(-3))    //'hello world'
console.log(string.substring(3,-4))  //'hel'
字符串位置方法
var string = 'hello world'
console.log(string.indexOf('o'))        //4
console.log(string.lastIndexOf('o'))    //7

可以循环调用indexOf()或lastIndexOf()来找到所有匹配的子字符串

var string = 'Lorem ipsum dolor sit amet, consectetur adipisicing elit'
var positions = new Array()
var pos = stringValue.indexOf('e', pos + 1)

while(pos > -1){
  positions.push(pos)
  pos =  string.indexOf('e', pos + 1)
}

console.log(positions)      //'3,24,32,35,52'
字符串大小写转换方法
字符串的模式匹配方法

String类型定义了几个用于在字符串中匹配模式的方法

var text = 'cat, bat, sat, fat'
var pattern = /.at/

var matches = text.match(pattern)
//与pattern.exec(text)相同
console.log(matches.index)        //0
console.log(matches[0])           //'cat'
console.log(pattern.lastIndex)    //0
var text = 'cat, bat, sat, fat'
var pos = text.search(/at/)
console.log(pos)                //1

如果想替换所有匹配的字符串,唯一的办法就是提供一个正则表达式

var text = 'cat, bat, sat, fat'
var result = text.replace('at','ond')
console.log(result)   //'cond,bat,sat,fat'

result = text.replace(/at/g, 'ond')
console.log(result)   //'cond,bond,sond,fond'

如果第二个参数是字符串,还可以用一些特殊的字符序列

var text = 'cat, bat, sat, fat'
result = text.replace(/(.at)/g,'word($1)')

replace()的第二个参数也可以是一个函数。
在只有一个匹配项的情况下,会向这个函数传递3个参数:模式的匹配项模式匹配项在字符串中的位置原始字符串

function htmlEscape(text){
  return text.replace(/[<>'&]/g, function(match,pos,originalText){
  switch(match){
      case '<':
        return '&lt;'
      case '>':
        return '&gt;'
      case '&':
        return '&amp;'
      case '\':
        return '&quot;'
    }
  })
}

单体内置对象

URI(标识、定位任何资源的字符串)

var uri = 'http://www.wrox.com/illegal value.htm#start'
console.log(encodeURI(uri))            
console.log(encodeURIComponent(uri))

eval()
eval()中创建的任何变量或函数都不会被提升,在解析代码的时候,他们被包含在一个字符串中

上一篇下一篇

猜你喜欢

热点阅读