JavaScript 从入门到精通

柳三千

目录

  1. JavaScript 基础核心
  2. 函数与作用域
  3. 对象与面向对象编程
  4. 数组操作
  5. 异步编程
  6. DOM 操作
  7. 现代 JavaScript (ES6+)
  8. 模块化开发
  9. 错误处理与调试
  10. 设计模式
  11. 性能优化
  12. 结语

1. JavaScript 基础核心

JavaScript 是一种动态类型的解释型语言,遵循 ECMAScript 标准。

变量声明

// var (函数作用域)
var oldWay = "Avoid in modern JS";

// let (块级作用域,可重新赋值)
let counter = 0;
counter = 1;

// const (块级作用域,常量)
const PI = 3.14159;
// PI = 3; // 错误!常量不可重新赋值

数据类型

// 原始类型
const str = "Hello";
const num = 42;
const bool = true;
const empty = null;
const notDefined = undefined;
const sym = Symbol('unique');

// 引用类型
const obj = { key: "value" };
const arr = [1, 2, 3];
const func = function() {};

// 类型检测
console.log(typeof str); // "string"
console.log(arr instanceof Array); // true

运算符

// 算术运算符
console.log(10 + 5); // 15
console.log(10 % 3); // 1

// 比较运算符
console.log(5 == "5"); // true (值相等)
console.log(5 === "5"); // false (类型不同)

// 逻辑运算符
console.log(true && false); // false
console.log(false || true); // true
console.log(!true); // false

控制流

// if/else
const age = 18;
if (age >= 18) {
  console.log("Adult");
} else {
  console.log("Minor");
}

// switch
const fruit = "apple";
switch(fruit) {
  case "banana":
    console.log("Yellow");
    break;
  case "apple":
    console.log("Red");
    break;
  default:
    console.log("Unknown");
}

// 三元运算符
const message = age >= 18 ? "Adult" : "Minor";

2. 函数与作用域

函数是 JavaScript 的一等公民。

函数声明与表达式

// 函数声明
function add(a, b) {
  return a + b;
}

// 函数表达式
const multiply = function(a, b) {
  return a * b;
};

// 箭头函数 (ES6+)
const divide = (a, b) => a / b;

作用域与闭包

// 词法作用域
function outer() {
  const outerVar = "I'm outside!";
  
  function inner() {
    console.log(outerVar); // 访问外部变量
  }
  
  return inner;
}

const closureExample = outer();
closureExample(); // "I'm outside!"

// 闭包应用:私有变量
function createCounter() {
  let count = 0;
  
  return {
    increment: () => count++,
    getCount: () => count
  };
}

const counter = createCounter();
counter.increment();
console.log(counter.getCount()); // 1

高阶函数

// 函数作为参数
function processArray(arr, processor) {
  return arr.map(processor);
}

const doubled = processArray([1, 2, 3], x => x * 2);
console.log(doubled); // [2, 4, 6]

// 函数作为返回值
function createMultiplier(factor) {
  return function(x) {
    return x * factor;
  };
}

const triple = createMultiplier(3);
console.log(triple(5)); // 15

3. 对象与面向对象编程

对象创建

// 对象字面量
const person = {
  name: "Alice",
  age: 30,
  greet() {
    console.log(`Hello, I'm ${this.name}`);
  }
};

person.greet(); // "Hello, I'm Alice"

// 构造函数
function Person(name, age) {
  this.name = name;
  this.age = age;
}

Person.prototype.greet = function() {
  console.log(`Hi, I'm ${this.name}`);
};

const bob = new Person("Bob", 25);
bob.greet(); // "Hi, I'm Bob"

// ES6类
class Animal {
  constructor(name) {
    this.name = name;
  }
  
  speak() {
    console.log(`${this.name} makes a noise`);
  }
}

class Dog extends Animal {
  constructor(name) {
    super(name);
  }
  
  speak() {
    console.log(`${this.name} barks`);
  }
}

const dog = new Dog("Rex");
dog.speak(); // "Rex barks"

this 关键字

const car = {
  brand: "Tesla",
  start: function() {
    console.log(`Starting ${this.brand}`);
  }
};

car.start(); // "Starting Tesla"

// this 绑定问题
const startFn = car.start;
startFn(); // "Starting undefined" (this指向全局)

// 解决方案
const boundStart = car.start.bind(car);
boundStart(); // "Starting Tesla"

// 箭头函数没有自己的this
const timer = {
  seconds: 0,
  start() {
    setInterval(() => {
      this.seconds++;
      console.log(this.seconds);
    }, 1000);
  }
};

timer.start(); // 每秒递增seconds

4. 数组操作

基本方法

const numbers = [1, 2, 3, 4, 5];

// 添加/删除元素
numbers.push(6); // 末尾添加
numbers.pop();   // 末尾删除
numbers.unshift(0); // 开头添加
numbers.shift();    // 开头删除

// 切片
const slice = numbers.slice(1, 3); // [2, 3]

高阶数组方法

// map - 转换数组
const squares = numbers.map(n => n * n); // [1, 4, 9, 16, 25]

// filter - 过滤元素
const evens = numbers.filter(n => n % 2 === 0); // [2, 4]

// reduce - 累积值
const sum = numbers.reduce((acc, curr) => acc + curr, 0); // 15

// find - 查找元素
const firstEven = numbers.find(n => n % 2 === 0); // 2

// every/some - 条件检查
const allPositive = numbers.every(n => n > 0); // true
const hasNegative = numbers.some(n => n < 0); // false

实用数组技巧

// 数组合并
const arr1 = [1, 2];
const arr2 = [3, 4];
const combined = [...arr1, ...arr2]; // [1, 2, 3, 4]

// 数组去重
const duplicates = [1, 2, 2, 3, 4, 4, 5];
const unique = [...new Set(duplicates)]; // [1, 2, 3, 4, 5]

// 数组解构
const [first, second, ...rest] = numbers;
console.log(first); // 1
console.log(rest); // [3, 4, 5]

5. 异步编程

回调函数

function fetchData(callback) {
  setTimeout(() => {
    callback("Data received");
  }, 1000);
}

fetchData(data => {
  console.log(data); // "Data received" (1秒后)
});

Promise

function asyncOperation() {
  return new Promise((resolve, reject) => {
    setTimeout(() => {
      Math.random() > 0.5 
        ? resolve("Success!") 
        : reject("Error!");
    }, 1000);
  });
}

asyncOperation()
  .then(result => console.log(result))
  .catch(error => console.error(error));

async/await

async function fetchUserData() {
  try {
    const response = await fetch('https://api.example.com/user');
    const data = await response.json();
    console.log(data);
    return data;
  } catch (error) {
    console.error("Fetch failed:", error);
  }
}

fetchUserData();

并发控制

// 并行执行
Promise.all([
  fetch('/api/users'),
  fetch('/api/posts')
]).then(([users, posts]) => {
  console.log(users, posts);
});

// 竞速执行
Promise.race([
  fetch('/api/fast'),
  new Promise((_, reject) => 
    setTimeout(() => reject(new Error('Timeout')), 5000)
  )
]).then(data => console.log(data))
  .catch(err => console.error(err));

6. DOM 操作

元素选择与操作

// 选择元素
const header = document.getElementById('header');
const buttons = document.querySelectorAll('.btn');
const container = document.querySelector('.container');

// 创建元素
const newDiv = document.createElement('div');
newDiv.textContent = "New Element";
container.appendChild(newDiv);

// 修改样式
header.style.backgroundColor = '#f0f0f0';
buttons.forEach(btn => {
  btn.classList.add('active');
});

// 事件监听
const submitBtn = document.getElementById('submit');
submitBtn.addEventListener('click', event => {
  event.preventDefault();
  console.log('Form submitted');
});

事件委托

document.getElementById('list').addEventListener('click', event => {
  if (event.target.classList.contains('item')) {
    console.log('Item clicked:', event.target.textContent);
  }
});

动态内容渲染

function renderUserList(users) {
  const list = document.getElementById('user-list');
  list.innerHTML = ''; // 清空列表
  
  users.forEach(user => {
    const li = document.createElement('li');
    li.className = 'user-item';
    li.innerHTML = `
      <img src="${user.avatar}" alt="${user.name}">
      <span>${user.name}</span>
    `;
    list.appendChild(li);
  });
}

7. 现代 JavaScript (ES6+)

解构赋值

// 对象解构
const user = { name: 'Alice', age: 30, city: 'Paris' };
const { name, age } = user;
console.log(name, age); // "Alice" 30

// 数组解构
const colors = ['red', 'green', 'blue'];
const [firstColor, , thirdColor] = colors;
console.log(firstColor, thirdColor); // "red" "blue"

// 函数参数解构
function printUser({ name, age }) {
  console.log(`${name} is ${age} years old`);
}
printUser(user); // "Alice is 30 years old"

模板字符串

const product = "JavaScript Book";
const price = 29.99;
const quantity = 3;

const summary = `
  Product: ${product}
  Price: $${price}
  Quantity: ${quantity}
  Total: $${(price * quantity).toFixed(2)}
`;
console.log(summary);

默认参数与剩余参数

// 默认参数
function greet(name = "Guest") {
  console.log(`Hello, ${name}!`);
}

// 剩余参数
function sum(...numbers) {
  return numbers.reduce((acc, num) => acc + num, 0);
}
console.log(sum(1, 2, 3, 4)); // 10

可选链与空值合并

const user = {
  profile: {
    name: "Alice",
    address: {
      city: "Paris"
    }
  }
};

// 可选链
console.log(user.profile?.address?.city); // "Paris"
console.log(user.settings?.theme); // undefined

// 空值合并
const theme = user.settings?.theme ?? "light";
console.log(theme); // "light"

8. 模块化开发

ES 模块

// math.js
export const PI = 3.14159;

export function add(a, b) {
  return a + b;
}

export default function multiply(a, b) {
  return a * b;
}

// app.js
import { PI, add } from './math.js';
import multiply from './math.js';

console.log(PI); // 3.14159
console.log(add(2, 3)); // 5
console.log(multiply(4, 5)); // 20

动态导入

button.addEventListener('click', async () => {
  const module = await import('./dialog.js');
  module.openDialog('Hello!');
});

9. 错误处理与调试

try/catch

try {
  // 可能出错的代码
  JSON.parse('invalid json');
} catch (error) {
  console.error("Parsing error:", error.message);
} finally {
  console.log("Cleanup operations");
}

自定义错误

class ValidationError extends Error {
  constructor(message) {
    super(message);
    this.name = "ValidationError";
  }
}

function validateEmail(email) {
  if (!email.includes('@')) {
    throw new ValidationError("Invalid email format");
  }
}

try {
  validateEmail("example.com");
} catch (error) {
  if (error instanceof ValidationError) {
    console.error("Validation failed:", error.message);
  } else {
    throw error; // 重新抛出未知错误
  }
}

10. 设计模式

单例模式

class Logger {
  constructor() {
    if (Logger.instance) {
      return Logger.instance;
    }
    this.logs = [];
    Logger.instance = this;
  }
  
  log(message) {
    this.logs.push(message);
    console.log(`LOG: ${message}`);
  }
  
  printLogCount() {
    console.log(`${this.logs.length} logs`);
  }
}

// 使用
const logger1 = new Logger();
const logger2 = new Logger();

logger1.log("First log");
logger2.log("Second log");

logger1.printLogCount(); // "2 logs"
console.log(logger1 === logger2); // true

观察者模式

class EventEmitter {
  constructor() {
    this.events = {};
  }
  
  on(event, listener) {
    if (!this.events[event]) {
      this.events[event] = [];
    }
    this.events[event].push(listener);
  }
  
  emit(event, ...args) {
    if (this.events[event]) {
      this.events[event].forEach(listener => {
        listener(...args);
      });
    }
  }
  
  off(event, listener) {
    if (this.events[event]) {
      this.events[event] = this.events[event].filter(
        l => l !== listener
      );
    }
  }
}

// 使用
const emitter = new EventEmitter();

const logData = data => console.log("Received:", data);

emitter.on("data", logData);
emitter.emit("data", { id: 1, value: "test" }); // 输出数据

emitter.off("data", logData);
emitter.emit("data", "This won't be logged");

11. 性能优化

防抖与节流

// 防抖 - 连续触发后只执行一次
function debounce(func, delay) {
  let timer;
  return function(...args) {
    clearTimeout(timer);
    timer = setTimeout(() => {
      func.apply(this, args);
    }, delay);
  };
}

// 节流 - 固定间隔执行一次
function throttle(func, limit) {
  let inThrottle;
  return function(...args) {
    if (!inThrottle) {
      func.apply(this, args);
      inThrottle = true;
      setTimeout(() => (inThrottle = false), limit);
    }
  };
}

// 使用
window.addEventListener('resize', throttle(() => {
  console.log('Resize handler called');
}, 500));

性能分析

console.time('Array Processing');

// 性能关键代码
const bigArray = Array(1000000).fill().map(() => Math.random());
const sorted = bigArray.sort((a, b) => a - b);

console.timeEnd('Array Processing'); // 输出执行时间

内存管理

// 避免内存泄漏
function setup() {
  const element = document.getElementById('myElement');
  const data = new Array(1000000).fill('data');
  
  element.addEventListener('click', () => {
    console.log(data.length);
  });
  
  // 清理函数
  return () => {
    element.removeEventListener('click');
    // 清除大数组引用
    data.length = 0;
  };
}

const cleanup = setup();

// 当不再需要时
cleanup();

12. 结语

通过掌握本白皮书涵盖的知识点,你已经具备了从初级到高级的 JavaScript 开发能力。关键要点:

  1. 核心概念:理解作用域、闭包、原型链等基础
  2. 现代语法:熟练使用 ES6+ 特性提升开发效率
  3. 异步编程:掌握 Promise、async/await 处理异步操作
  4. 工程实践:运用模块化、设计模式构建可维护应用
  5. 性能意识:优化关键路径,避免常见陷阱

精通之路:不断实践,参与开源项目,阅读源码,解决复杂问题。JavaScript 生态系统不断发展,持续学习是成为专家的关键!

// 你的JavaScript之旅从这里开始
console.log("Hello, JavaScript Master!");

学习资源:

文章版权声明:除非注明,否则均为柳三千运维录原创文章,转载或复制请以超链接形式并注明出处。

取消
微信二维码
微信二维码
支付宝二维码