一、创建对象三种方式
1.利用对象字面量创建对象
2.利用 new Object 创建对象
3.利用构造函数创建对象
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta http-equiv="X-UA-Compatible" content="IE=edge">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>创建对象的三种方式</title>
</head>
<body>
<script>
// 1. 使用对象字面量创建对象
const o1 = {
name: '淳佳静',
age: 16
}
console.log(o1)
// 2. new Object() 创建对象, 创建后添加属性
const o2 = new Object()
o2.name = '小佳静'
o2.age = 18
console.log(o2)
// 3. new Object() 创建时就添加属性
const o3 = new Object({
name: '小淳',
age: 19
})
console.log(o3)
// 以上两种创建对象的方式, 可以理解为完全相同, 字面量就是 new Object() 的简写形式
</script>
</body>
</html>
效果展示:
二、构造函数
1.构造函数 :是一种特殊的函数,主要用来创建对象(初始化对象)
2.使用场景:常规的 {...} 语法允许创建一个对象。比如我们创建了佩奇的对象,继续创建乔治的对象还需要重新写一遍,此时可以通过构造函数来快速创建多个类似的对象
3.构造函数在技术上是常规函数 不过有两个约定: 它们的命名以大写字母开头 通过 new 关键字来调用构造函数,可以创建对象
4.说明:
4.1 使用 new 关键字调用函数的行为被称为实例化
4.2 实例化构造函数时没有参数时可以省略 ()
4.3 构造函数内部无需写return,返回值即为新创建的对象
4.4 new Object() new Date() 也是实例化构造函数
5.特点:
5.1 调用构造函数会自动创建一个新对象
5.2 将函数中的 this 指向这个新对象
5.3 执行函数的代码, 可以给当前创建的新对象添加属性
5.4 默认返回这个新对象, 不需要写 return
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta http-equiv="X-UA-Compatible" content="IE=edge">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>构造函数</title>
</head>
<body>
<script>
// 需求: 创建多个同学对象, 每个同学对象都有自己的名字/年龄/爱好
// let s1 = {
// name: '龙志豪',
// age: 18,
// hobby: '喷火'
// }
// let s2 = {
// name: '陈厚霖',
// age: 18,
// hobby: '收作业'
// }
// 构造函数: 一种特殊的函数, 专门用于帮助程序员创建对象的
// 构造函数本质就是普通函数, 只有在使用 new 关键字调用它的时候, 就被称为构造函数
// 定义时和普通函数没有任何区别, 只有在调用时才能决定它是否为构造函数
// 特点:
// 1. 调用构造函数会自动创建一个新对象
// 2. 将函数中的 this 指向这个新对象
// 3. 执行函数的代码, 可以给当前创建的新对象添加属性
// 4. 默认返回这个新对象, 不需要写 return
function Student(name, age, hobby) {
// console.log('你好我是 Student 函数')
// this => 指向刚刚我们创建的那个新对象
// 新对象就是实例, this 指向它, this.name 就是给实例添加属性
// this.name 就是实例属性
this.name = name
this.age = age
this.hobby = hobby
this.study = function() {
console.log(this.name + '在学习')
}
}
const s1 = new Student('古力娜扎', 19, '跳舞')
// 可以添加属性
// s1.name = '古力娜扎'
// s1.age = 19
console.log(s1)
s1.study()
const s2 = new Student('大张伟', 19, '摇滚')
// 可以添加属性, 但不方便
// s2.name = '大张伟'
// s2.age = 19
console.log(s2)
s2.study()
const s3 = new Student('薛之谦', 18, '冷笑话')
console.log(s3)
s3.study()
// 全等比较是比较地址值
console.log(s1 === s2)
console.log(s1 === s3)
console.log(s2 === s3)
const ss1 = s1
console.log(s1 === ss1)
// 实例是什么? new 构造函数创建的对象就是实例
// 实例成员: 实例身上的属性或方法
// 这些成员都是存在实例上面的, 所以不同的实例之间成员无不干扰
// 静态成员: 构造函数身上的属性或方法
// 这些成员是存在构造函数身上的, 一般存储一些所有对象都公共的属性或方法
Student.sleep = function() {
console.log('学生在睡觉', this)
}
Student.eat = function() {
console.log('学生在干饭')
}
Student.eyes = 2
// Date.now()
Student.sleep()
// new String()
// let str = '123'
// new Number()
// let num = 123
// num.
</script>
</body>
</html>
效果展示:
三、实例成员&静态成员
3.1 实例成员
通过构造函数创建的对象称为实例对象,实例对象中的属性和方法称为实例成员(实例属性和实例方法)
说明:
1. 为构造函数传入参数,创建结构相同但值不同的对象
2.实例对象的属性和方法即为实例成员
3.实例对象相互独立,实例成员当前实例对象使用
3.2 静态成员
构造函数的属性和方法被称为静态成员(静态属性和静态方法)
说明:
1.构造函数的属性和方法被称为静态成员
2. 静态成员只能构造函数来访问
3. 静态方法中的this指向构造函数
比如 Date.now()
四、一切皆对象
引用类型: Object,Array,RegExp,Date 等
基本数据类型: 字符串、数值、布尔、undefined、null 等
其实字符串、数值、布尔、等基本类型也都有专门的构造函数,这些我们称为包装类型
包装类型 String,Number,Boolean
包装类型执行过程: 创建一个 String 类型的实例 调用实例上的特定方法 销毁实例 JS中几乎所有的数据都可以基于构造函数创建,不同的构造器创建出来的数据拥有不同的属性和方法
五、内置构造函数
Object 是内置的构造函数,用于创建普通对象。
推荐使用字面量方式声明对象,而不是 Object 构造函数
只能给构造函数使用的方法是静态方法
5.1 Object
Object.keys() 静态方法获取对象中所有属性(键);返回的是一个数组
Object.values() 静态方法获取对象中所有属性值;返回的是一个数组
Object. assign() 静态方法常用于对象拷贝
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta http-equiv="X-UA-Compatible" content="IE=edge">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>Object</title>
</head>
<body>
<script>
// const o1 = new Object()
// o1.toString() // 实例方法
// Object.values() // 静态方法
// 需求: 循环取出对象所有的属性名和属性值
const o = {
name: '大神',
age: 18,
hobby: '懂 JS'
}
// 老方法: for-in
// for (let k in o) {
// console.log(k)
// console.log(o[k])
// }
// 新方法: Object.keys()
// 作用: 获取对象所有的键 (属性名)
// 参数1: 传入对象
// 返回值: 数组
// const keys = Object.keys(o)
// keys.forEach(k => console.log(k))
// console.log(keys)
// Object.keys(o).forEach(k => console.log(k))
// 新方法: Object.values()
// 作用: 获取对象所有的值 (属性值)
// 参数1: 传入对象
// 返回值: 数组
// const values = Object.values(o)
// console.log(values.join('-'))
// 拷贝对象
// Object.assign()
// const o2 = o // 只是复制了地址值, 不是拷贝对象
// o2.name = '小赵'
// console.log(o)
// console.log(o2)
// 老方法
// const o2 = {}
// for (let k in o) {
// // console.log(k)
// // console.log(o[k])
// o2[k] = o[k]
// }
// o2.name = '小赵'
// console.log(o)
// console.log(o2)
// 新方法
// Object.assign()
// 作用: 将源对象的所有属性复制给目标对象
// 参数1: 目标对象
// 参数2: 源对象
// 返回值: 拷贝好的目标对象
const o2 = Object.assign({}, o)
o2.name = '小赵'
console.log(o)
console.log(o2)
</script>
</body>
</html>
效果展示:
5.2 Array
Array 是内置的构造函数,用于创建数组,创建数组建议使用字面量创建,不用 Array构造函数创建
reduce 执行过程:
1. 如果没有起始值, 则上一次值以数组的第一个数组元素的值
2. 每一次循环,把返回值给做为 下一次循环的上一次值
3. 如果有起始值,则 起始值做为上一次值
更形象的图解阐述:
数组的更多方法图解:
reduce案例展示:
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta http-equiv="X-UA-Compatible" content="IE=edge">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>reduce</title>
</head>
<body>
<script>
// reduce() 累加器
// 作用: 一般用于求和, 可以将数组中所有的元素进行累加
const arr = [1, 2, 3, 4, 5]
// let sum = 0
// arr.forEach(item => {
// forEach 的回调函数:
// 参数1: 遍历的每一个元素
// 参数2: 索引
// sum += item
// })
// console.log(sum)
// 参数1: 回调函数
// 前一次的值, 遍历的每一个元素
// 参数2: 初始值
// 如果没有传第二个参数, 则会默认把数组的第一个元素作为初始值, 并且遍历会从第二个元素开始(索引为 1 开始)
// 返回值: 和
// 第一次循环: prev 1 item 2 返回值 3
// 第二次循环: prev 3 item 3 返回值 6
// 第三次循环: prev 6 item 4 返回值 10
// 第四次循环: prev 10 item 5 返回值 15
// 结束循环, 把 15 给 reduce 来返回
let sum = arr.reduce((prev, item) => {
console.log('我是 reduce 执行的')
return prev + item
})
console.log(sum)
</script>
</body>
</html>
效果展示:
数组常见方法- 伪数组转换为真数组
常见伪数组
1. 函数里的arguments对象
2. querySelectorAll 等获得
3. 元素.children
4.注意: querySelectorAll 里面可以使用 forEach方法
转换为真数组:
静态方法 Array.from()
返回:新数组(真数组)
不修改原来的伪数组
5.3 String
5.5 Number
Number 是内置的构造函数,用于创建数值
常用方法: toFixed(保留位数长度) 设置保留小数位的长度