# 1. React ## 1.1 脚手架文件结构 ``` ├── node_modules ├── public │ ├── favicon.ico: 页签图标 │ └── index.html: 主页面 ├── src │ ├── assets: 存放静态资源 │ │ └── logo.svg │ ├── components: 存放组件 │ │ └── HelloWorld.jsx │ ├── App.jsx: 汇总所有组件 │ └── index.js: 入口文件 ├── .gitignore: git版本管制忽略的配置 ├── package.json: 应用包配置文件 ├── README.md: 应用描述文件 └── package-lock.json:包版本控制文件 ``` ## 1.2 React 核心概念 ### 1.2.1 JSX #### 1. 定义 JSX 是 JavaScript XML 的缩写,它允许在 JavaScript 代码中编写类似 HTML 的结构,最终会被 Babel 等工具编译为 React 元素。 #### 2. 基本语法 JSX 看起来像 HTML,但实际上是 JavaScript 语法扩展,必须包含在一个根元素中。示例: ```jsx const element = (

Hello, world!

Welcome to React.

); ``` #### 3. 表达式嵌入 在 JSX 中可以使用花括号 `{}` 嵌入 JavaScript 表达式。示例: ```jsx const name = 'Alice'; const element =

Hello, {name}

; ``` #### 4. 样式处理 在 JSX 中使用 `style` 属性设置内联样式,属性值为一个 JavaScript 对象,键采用驼峰命名法。示例: ```jsx const element =
Styled text
; ``` #### 5. 类名设置 由于 `class` 是 JavaScript 保留字,在 JSX 中使用 `className` 来设置 HTML 元素的类名。示例: ```jsx const element =
Container element
; ``` ### 1.2.2 组件 #### 1. 函数组件 函数组件是一个返回 JSX 的 JavaScript 函数,接收 `props` 作为参数。示例: ```jsx function Welcome(props) { return

Hello, {props.name}

; } ``` #### 2. 类组件 类组件继承自 `React.Component`,必须实现 `render` 方法返回 JSX。示例: ```jsx class Welcome extends React.Component { render() { return

Hello, {this.props.name}

; } } ``` ### 1.2.6 事件处理 在 React 中,事件处理与 HTML 类似,但采用驼峰命名法,并且通过传递函数来处理事件。示例: ```jsx function Button() { const handleClick = () => { alert('Button clicked!'); }; return ( ); } ``` ### 1.2.7 条件渲染 在 React 中可以使用 JavaScript 逻辑进行条件渲染。示例: ```jsx function Greeting(props) { const isLoggedIn = props.isLoggedIn; if (isLoggedIn) { return

Welcome back!

; } return

Please sign up.

; } ``` 还可以使用三元运算符和逻辑与运算符进行条件渲染: ```jsx // 三元运算符 const element = isLoggedIn ? : ; // 逻辑与运算符 const unreadMessages = ['React', 'Re: React', 'Re:Re: React']; const element = (

Hello!

{unreadMessages.length > 0 && (

You have {unreadMessages.length} unread messages.

)}
); ``` ### 1.2.3 状态(State) 1. 功能:用于管理组件内部的数据。 2. 示例: ```jsx class Counter extends React.Component { constructor(props) { super(props); this.state = { count: 0 }; } increment = () => { this.setState({ count: this.state.count + 1 }); }; render() { return (

Count: {this.state.count}

); } } ``` ### 1.2.4 生命周期方法 1. `componentDidMount()`:组件挂载后执行,常用于数据请求。 2. `componentDidUpdate()`:组件更新后执行。 3. `componentWillUnmount()`:组件卸载前执行,常用于清理工作。 ### 1.2.5 状态提升 当多个组件需要共享状态时,通常会将状态提升到最近的共同父组件中。通过父组件传递 `props` 和回调函数,实现子组件与父组件之间的状态同步。 ```jsx class Counter extends React.Component { constructor(props) { super(props); this.state = { count: 0 }; } increment = () => { this.setState({ count: this.state.count + 1 }); }; render() { return (

Count: {this.state.count}

); } } ``` ## 1.3 React Hooks ### 1.3.1 useState `useState` 是一个基础的 Hook,用于在函数组件中添加状态。示例如下: ```jsx import React, { useState } from 'react'; function Counter() { const [count, setCount] = useState(0); return (

You clicked {count} times

); } ``` ### 1.3.2 useEffect `useEffect` 可以让你在函数组件中执行副作用操作,比如数据获取、订阅或手动修改 DOM。示例如下: ```jsx import React, { useState, useEffect } from 'react'; function Example() { const [count, setCount] = useState(0); useEffect(() => { document.title = `You clicked ${count} times`; }, [count]); return (

You clicked {count} times

); } ``` ## 1.4 React 路由 ### 1.4.1 基本使用 1. 安装:`npm install react-router-dom` 2. 示例: ```jsx import React from 'react'; import { BrowserRouter as Router, Routes, Route, Link } from 'react-router-dom'; function App() { return ( } /> } /> ); } function Home() { return

Home Page

; } function About() { return

About Page

; } ``` ## 1.5 React 上下文(Context) ### 1.5.1 功能 用于在组件树中共享数据,避免逐层传递 props。 ### 1.5.2 示例 ```jsx import React, { createContext, useContext } from 'react'; const ThemeContext = createContext(); function App() { return ( ); } function Toolbar() { return (
); } function ThemedButton() { const theme = useContext(ThemeContext); return ; } ``` ## 1.6 React 优化 ### 1.6.1 `React.memo` 用于优化函数组件,避免不必要的渲染。 ```jsx const MyComponent = React.memo(function MyComponent(props) { /* 使用 props 渲染 */ }); ``` ### 1.6.2 `useCallback` 和 `useMemo` 1. `useCallback`:缓存函数,避免每次渲染都重新创建。 - **原理**:`useCallback` 接收一个回调函数和依赖项数组作为参数,返回一个 memoized 版本的回调函数,该回调函数仅在某个依赖项改变时才会更新。这有助于在传递回调函数给子组件时,避免不必要的重新渲染。 - **使用场景**:当你将回调函数作为 props 传递给子组件,并且子组件使用 `React.memo` 进行优化时,使用 `useCallback` 可以确保子组件不会因为回调函数的变化而不必要地重新渲染。 - **示例代码**: ```jsx import React, { useState, useCallback } from 'react'; function Parent() { const [count, setCount] = useState(0); const [value, setValue] = useState(''); // 使用 useCallback 缓存函数 const handleClick = useCallback(() => { console.log(`Count is: ${count}`); }, [count]); return (
setValue(e.target.value)} />
); } const Child = React.memo(function Child({ handleClick }) { return ( ); }); ``` 2. `useMemo`:缓存计算结果,避免重复计算。 - **原理**:`useMemo` 接收一个计算函数和依赖项数组作为参数,返回一个 memoized 的计算结果。仅当某个依赖项改变时,才会重新执行计算函数。 - **使用场景**:当你有一个计算开销较大的函数,并且该函数的输入依赖于某些状态或 props 时,使用 `useMemo` 可以避免在每次渲染时都重新计算结果。 - **示例代码**: ```jsx import React, { useState, useMemo } from 'react'; function App() { const [count, setCount] = useState(0); const [value, setValue] = useState(''); // 使用 useMemo 缓存计算结果 const expensiveValue = useMemo(() => { console.log('Calculating expensive value...'); let sum = 0; for (let i = 0; i < count; i++) { sum += i; } return sum; }, [count]); return (
setValue(e.target.value)} />

Expensive Value: {expensiveValue}

); } ```