玩转JavaScript对象与数组:从CRUD到函数式编程

玩转JavaScript对象与数组:从CRUD到函数式编程

一、对象基础与操作
1.1 对象字面量与属性

对象是JavaScript中存储和组织数据的核心结构,可以把它想象成一个“装东西的盒子”,而属性就是盒子里的内容。

// 创建对象
const person = {
  name: "张三",
  age: 25,
  address: {
    city: "北京",
    street: "朝阳区"
  },
  greet: function() {
    console.log(`你好,我叫${this.name}`);
  }
};

生活化比喻:对象就像一个书包,属性是书包里的书本、文具等,方法是书包上的拉链或口袋。

1.2 属性操作方式

对象的属性可以通过点符号或方括号访问。点符号适合固定键名,而方括号适合动态键名。

// 访问属性
console.log(person.name); // 点符号访问
console.log(person["age"]); // 方括号访问

// 添加新属性
person.email = "[email protected]";

// 删除属性
delete person.age;

// 调用方法
person.greet(); // 你好,我叫张三!

动态键名示例

const key = "name";
console.log(person[key]); // 张三
二、数组操作全攻略
2.1 基础CRUD操作

数组是存储有序数据的容器,可以动态增删改查。

const cart = ["苹果", "香蕉", "橙子"];

// 添加元素
cart.push("草莓"); // 尾部添加
cart.unshift("西瓜"); // 头部添加

// 删除元素
cart.pop(); // 删除尾部
cart.shift(); // 删除头部
cart.splice(1, 1); // 删除指定位置(从索引1开始删除1个元素)

// 修改元素
cart[0] = "哈密瓜";

// 查找元素
console.log(cart.indexOf("香蕉")); // 返回索引
console.log(cart.includes("橙子")); // 判断是否存在
2.2 slice与splice对比

slice 提取子数组,不修改原数组;splice 修改原数组。

方法 用途 返回值 是否修改原数组
slice 提取子数组 返回新数组
splice 添加/删除/替换元素 返回被删除的元素数组

示例

const fruits = ["苹果", "香蕉", "橙子"];
const subFruits = fruits.slice(1, 3); // ["香蕉", "橙子"]
fruits.splice(1, 1); // ["苹果", "橙子"]
三、高级特性应用
3.1 解构赋值

解构赋值是一种从对象或数组中快速提取值的方式。

// 对象解构
const { name, age } = person;
console.log(name, age); // 张三, 25

// 数组解构
const [first, second] = cart;
console.log(first, second); // 西瓜, 苹果

默认值与别名

const { name: userName = "默认用户", age: userAge = 18 } = person;
console.log(userName, userAge); // 张三, 25
3.2 展开运算符

展开运算符 ... 可以将数组或对象展开。

const newArray = [...cart, "葡萄"];
const newObject = { ...person, email: "[email protected]" };

合并数组与对象

const arr1 = [1, 2];
const arr2 = [3, 4];
const merged = [...arr1, ...arr2]; // [1, 2, 3, 4]

const obj1 = { a: 1 };
const obj2 = { b: 2 };
const mergedObj = { ...obj1, ...obj2 }; // { a: 1, b: 2 }
四、拷贝机制详解
4.1 浅拷贝与深拷贝对比

浅拷贝只复制对象的引用,而深拷贝会完全复制对象及其嵌套的内容。

浅拷贝示例

const shallowCopy = { ...person };
shallowCopy.name = "李四";
console.log(person.name); // 张三(原对象不受影响)

// 修改嵌套对象
shallowCopy.address.city = "上海";
console.log(person.address.city); // 上海(原对象受影响)

深拷贝示例

// 使用JSON方法(简单深拷贝,但无法处理函数、undefined等)
const deepCopy = JSON.parse(JSON.stringify(person));
deepCopy.address.city = "上海";
console.log(person.address.city); // 北京(原对象不受影响)

深拷贝的局限性

  • 无法处理函数、undefined 和循环引用。
  • 更复杂的深拷贝需要递归实现。
五、函数式编程实践
5.1 高阶函数应用

高阶函数是函数式编程的核心,可以简化代码并提高可读性。

forEach:遍历数组

cart.forEach(item => console.log(item));

map:创建新数组

const prices = [10, 20, 30];
const discountedPrices = prices.map(price => price * 0.9); // [9, 18, 27]

filter:筛选数组

const expensiveItems = prices.filter(price => price > 15); // [20, 30]

reduce:累加或聚合

const totalPrice = prices.reduce((sum, price) => sum + price, 0); // 60

find:查找第一个符合条件的元素

const item = cart.find(item => item === "苹果"); // "苹果"

生活化比喻

  • map 是流水线上的包装工人,逐个处理元素。
  • filter 是质检员,筛选出符合要求的元素。
  • reduce 是统计员,汇总所有元素的结果。
六、实战案例:学生数据处理

假设我们有一个学生数组,我们可以通过高阶函数实现以下功能:

const students = [
  { name: "张三", score: 85 },
  { name: "李四", score: 90 },
  { name: "王五", score: 70 }
];

// 筛选高分学生
const highScorers = students.filter(student => student.score >= 85);

// 计算平均分
const avgScore = students.reduce((sum, student) => sum + student.score, 0) / students.length;

// 格式化输出
const formatted = students.map(student => ({
  ...student,
  grade: student.score >= 85 ? "优秀" : "及格"
}));

console.log(highScorers, avgScore, formatted);
七、总结提升

本文从对象和数组的基础操作出发,逐步深入到解构赋值、拷贝机制和高阶函数等高级特性。掌握这些知识能够:

  1. 提高数据处理效率:通过高阶函数简化复杂操作。
  2. 编写更简洁优雅的代码:利用解构赋值和展开运算符减少冗余。
  3. 为函数式编程打下基础:理解不可变数据和纯函数的概念。
  4. 更好地理解JavaScript的核心机制:掌握引用类型和值类型的区别。

你可能感兴趣的:(JavaScript,前端,javascript,开发语言,笔记,经验分享)