大白话React第六章深入学习 React 高级特性及生态

news/2025/2/26 9:57:58

大白话React第六章深入学习 React 高级特性及生态

1. React Hooks 深入探究

React Hooks 就像是给你的 React 工具箱里添加了一堆超好用的小工具,让你在写函数组件的时候更轻松、更强大。

  • useEffect Hook:它就像一个“副作用管理器”。比如你要在组件加载的时候从服务器获取数据,或者在组件更新、卸载的时候做一些清理工作,都可以用它。
import React, { useState, useEffect } from'react';

const DataFetchingComponent = () => {
    const [data, setData] = useState([]);

    useEffect(() => {
        // 模拟从服务器获取数据
        const fetchData = async () => {
            const response = await fetch('https://api.example.com/data');
            const jsonData = await response.json();
            setData(jsonData);
        };

        fetchData();

        // 这里可以返回一个清理函数,在组件卸载时执行
        return () => {
            // 比如取消一个定时器或清除事件监听器
        };
    }, []);

    return (
        <div>
            <h2>数据获取组件</h2>
            <ul>
                {data.map((item, index) => (
                    <li key={index}>{item.name}</li>
                ))}
            </ul>
        </div>
    );
};

export default DataFetchingComponent;

在这个例子里,useEffect 里的函数在组件挂载时(因为依赖项数组为空 [])执行,去获取数据并更新状态。

  • useContext Hook:它能帮你轻松地在组件之间共享数据,就像在一个大家庭里,大家都能方便地拿到公共的东西。
import React, { createContext, useContext, useState } from'react';

// 创建一个 Context
const MyContext = createContext();

const ParentComponent = () => {
    const [sharedData, setSharedData] = useState('这是共享的数据');

    return (
        <MyContext.Provider value={{ sharedData, setSharedData }}>
            <ChildComponent />
        </MyContext.Provider>
    );
};

const ChildComponent = () => {
    const { sharedData, setSharedData } = useContext(MyContext);

    return (
        <div>
            <p>从 Context 中获取的数据: {sharedData}</p>
            <button onClick={() => setSharedData('数据被更新了')}>更新数据</button>
        </div>
    );
};

export default ParentComponent;

这里通过 createContext 创建了一个 Context,ParentComponent 作为提供者把数据和更新数据的函数传递下去,ChildComponentuseContext 轻松获取到共享数据并能更新它。

2. 学习 React 服务端渲染(SSR)

通常我们开发的 React 应用是在浏览器里运行的,页面先加载一个空壳,然后再填充数据。而服务端渲染就像是在服务器那边提前把页面内容都准备好,直接发给浏览器,这样页面加载速度会更快,对搜索引擎也更友好(搜索引擎能更好地抓取到内容)。

一个简单的基于 Next.js(一个常用的 React SSR 框架)的示例:

// pages/index.js
import React from'react';

const HomePage = () => {
    return (
        <div>
            <h1>欢迎来到服务端渲染的首页</h1>
            <p>这里的内容在服务器端就已经准备好啦。</p>
        </div>
    );
};

export default HomePage;

你需要先安装 Next.js,然后在项目目录下运行 npx create-next-app my-next-app 创建项目,把上面的代码放在 pages/index.js 文件里,运行 npm run dev,在浏览器里访问 http://localhost:3000 就能看到效果。

3. 了解 React 与 GraphQL 的结合

GraphQL 是一种数据查询语言,它能让你更灵活地获取数据。和 React 结合使用时,就像你有了一个更智能的采购员,能准确地帮你采购你需要的数据。

假设你有一个 GraphQL 服务器,以下是一个简单的 React 组件获取 GraphQL 数据的示例(使用 @apollo/client 库):

import React from'react';
import { ApolloClient, InMemoryCache, ApolloProvider, useQuery, gql } from '@apollo/client';

// 创建 ApolloClient 实例
const client = new ApolloClient({
    uri: 'https://api.example.com/graphql', // 你的 GraphQL 服务器地址
    cache: new InMemoryCache()
});

const GET_DATA = gql`
    query {
        items {
            id
            name
        }
    }
`;

const DataComponent = () => {
    const { loading, error, data } = useQuery(GET_DATA);

    if (loading) return <p>加载中...</p>;
    if (error) return <p>获取数据出错: {error.message}</p>;

    return (
        <div>
            <h2>从 GraphQL 获取的数据</h2>
            <ul>
                {data.items.map((item) => (
                    <li key={item.id}>{item.name}</li>
                ))}
            </ul>
        </div>
    );
};

const App = () => {
    return (
        <ApolloProvider client={client}>
            <DataComponent />
        </ApolloProvider>
    );
};

export default App;

这里通过 ApolloClient 连接到 GraphQL 服务器,useQuery Hook 发送查询请求并获取数据,根据数据的加载状态和是否有错误来展示相应的内容。

4. 组件库开发与发布

当你开发了很多可复用的组件后,就可以把它们打包成一个组件库,就像把你的好用工具整理成一个工具箱,分享给别人用。

比如开发一个简单的按钮组件库:

// Button.js
import React from'react';

const Button = ({ text, onClick, color }) => {
    return (
        <button
            style={{ backgroundColor: color, padding: '10px 20px', borderRadius: '5px' }}
            onClick={onClick}
        >
            {text}
        </button>
    );
};

export default Button;

然后你可以用工具(如 rollup 等)把组件打包,发布到 npm 上,让其他开发者能安装使用你的组件库。

通过这些更深入的学习,你对 React 的掌握会更全面,能够开发出更复杂、更高效、更优质的应用。

除了React Hooks,React还有哪些高级特性?

除了React Hooks外,React还有以下一些高级特性:

上下文(Context)

  • 作用:用于在组件树中共享数据,避免了通过props一层一层地传递数据,特别是在多个组件都需要访问同一数据的情况下非常有用。
  • 使用示例
import React, { createContext, useContext } from 'react';

// 创建上下文
const ThemeContext = createContext();

const ThemeProvider = ({ children }) => {
    // 主题相关状态和方法
    const [theme, setTheme] = React.useState('light');
    const toggleTheme = () => {
        setTheme(theme === 'light'? 'dark' : 'light');
    };

    // 提供数据
    return (
        <ThemeContext.Provider value={{ theme, toggleTheme }}>
            {children}
        </ThemeContext.Provider>
    );
};

const ThemeButton = () => {
    // 消费数据
    const { theme, toggleTheme } = useContext(ThemeContext);

    return (
        <button style={{ backgroundColor: theme === 'light'? 'white' : 'black', color: theme === 'light'? 'black' : 'white' }} onClick={toggleTheme}>
            Toggle Theme
        </button>
    );
};

高阶组件(Higher-Order Components,HOC)

  • 作用:是一种复用组件逻辑的高级技术,它是一个函数,接受一个组件作为参数,并返回一个新的增强后的组件。可以用于添加额外的功能,如数据获取、性能优化、权限控制等。
  • 使用示例
import React from 'react';

// 高阶组件
const withLogging = (WrappedComponent) => {
    return class extends React.Component {
        componentDidMount() {
            console.log(`组件 ${WrappedComponent.name} 已挂载`);
        }

        componentWillUnmount() {
            console.log(`组件 ${WrappedComponent.name} 即将卸载`);
        }

        render() {
            return <WrappedComponent {...this.props} />;
        }
    };
};

// 被包装的组件
const MyComponent = () => {
    return <div>这是我的组件</div>;
};

// 使用高阶组件包装组件
const EnhancedComponent = withLogging(MyComponent);

错误边界(Error Boundaries)

  • 作用:用于捕获其子组件树中发生的JavaScript错误,并展示一个友好的错误界面,而不是让整个应用崩溃。可以帮助提高应用的稳定性和用户体验。
  • 使用示例
import React, { Component } from 'react';

class ErrorBoundary extends Component {
    constructor(props) {
        super(props);
        this.state = { hasError: false };
    }

    static getDerivedStateFromError(error) {
        // 更新状态以显示错误
        return { hasError: true };
    }

    componentDidCatch(error, errorInfo) {
        // 可以在这里记录错误日志
        console.log('捕获到错误:', error, errorInfo);
    }

    render() {
        if (this.state.hasError) {
            // 显示错误界面
            return <h1>哎呀,出了点问题!</h1>;
        }
        // 正常渲染子组件
        return this.props.children;
    }
}

const BrokenComponent = () => {
    // 故意抛出错误
    throw new Error('模拟错误');
    return <div>这个组件不会被渲染</div>;
};

const App = () => {
    return (
        <ErrorBoundary>
            <BrokenComponent />
        </ErrorBoundary>
    );
};

渲染属性(Render Props)

  • 作用:是一种在React组件之间共享代码的技术,通过将一个返回React元素的函数作为属性传递给组件,让组件可以根据不同的逻辑来渲染内容。
  • 使用示例
import React from 'react';

const MouseTracker = ({ render }) => {
    const [mousePosition, setMousePosition] = React.useState({ x: 0, y: 0 });

    const handleMouseMove = (event) => {
        setMousePosition({ x: event.clientX, y: event.clientY });
    };

    return (
        <div style={{ height: '100vh' }} onMouseMove={handleMouseMove}>
            {render(mousePosition)}
        </div>
    );
};

const App = () => {
    return (
        <MouseTracker render={(mousePosition) => (
            <p>鼠标位置:x = {mousePosition.x}, y = {mousePosition.y}</p>
        )} />
    );
};

http://www.niftyadmin.cn/n/5868512.html

相关文章

DiskGenius v5.6.1 硬盘管理 文件恢复 数据恢复 官方版

参考原文&#xff1a;DiskGenius v5.6.1 硬盘管理 文件恢复 数据恢复 官方版 软件介绍 老牌软件了&#xff0c;无论是数据恢复&#xff0c;磁盘管理都非常好用 DiskGenius&#xff0c;集数据恢复、分区管理、备份还原等多功能于一身的超级工具软件。DiskGenius是专业级的数据…

虚拟机 | Ubuntu 安装流程以及界面太小问题解决

提示&#xff1a;写完文章后&#xff0c;目录可以自动生成&#xff0c;如何生成可参考右边的帮助文档 文章目录 前言一、Ubuntu初识二、使用步骤1.下载ubuntu镜像2.创建虚拟机1、使用典型&#xff08;节省空间&#xff09;2、稍后安装方便配置3、优选Linux版本符合4、浏览位置&…

【Elasticsearch】使用Postman操作es的_bulk批量操作

众所周知&#xff0c;Elasticsearch的语法还是很恶心的。因此需要大量的调试&#xff0c;有些人在kibana上进行调试&#xff0c;但是如果想使用Postman进行调试时&#xff0c;大部分还是没有问题的。主要是bulk操作&#xff0c;有一些特殊性。关键问题在于换行这里。 如果你要…

nvm下载node版本npm下载失败

需要切换node版本&#xff0c;使用nvm作为管理工具。 安装node 10.24.1 nvm install 10.24.1 npm下载失败&#xff1a; 使用提示的网址下载npm压缩包&#xff08;https://github.com/npm/cli/archive/v6.14.12.zip&#xff09; 将压缩包内容解压到 nvm 对应node版本目录下…

flink operator v1.10对接华为云对象存储OBS

1 概述 flink operator及其flink集群&#xff0c;默认不直接支持华为云OBS&#xff0c;需要在这些java程序的插件目录放一个jar包&#xff0c;以及修改flink配置后&#xff0c;才能支持集成华为云OBS。 相关链接参考&#xff1a; https://support.huaweicloud.com/bestpracti…

论文笔记(七十二)Reward Centering(三)

Reward Centering&#xff08;三&#xff09; 文章概括摘要3 基于值的奖励中心化4 案例研究&#xff1a; 以奖励为中心的 Q-learning5 讨论、局限性与未来工作致谢 文章概括 引用&#xff1a; article{naik2024reward,title{Reward Centering},author{Naik, Abhishek and Wan…

洛谷 P8705:[蓝桥杯 2020 省 B1] 填空题之“试题 E :矩阵” ← 卡特兰数

【题目来源】 https://www.luogu.com.cn/problem/P8705 【题目描述】 把 1∼2020 放在 21010 的矩阵里。要求同一行中右边的比左边大&#xff0c;同一列中下边的比上边的大。一共有多少种方案? 答案很大&#xff0c;你只需要给出方案数除以 2020 的余数即可。 【答案提交】 …

ChatGPT免费背后的技术暗战 国产数字孪生如何打造“虚实共生”新生态?

当ChatGPT搜索功能向全球免费开放&#xff0c;AI技术的平民化时代正式来临。在这场看似“让利”的商业策略背后&#xff0c;实则是全球科技话语权的重新洗牌。国产厂商如何在这场博弈中占据主动&#xff1f;数字孪生技术的场景化落地提供了破局方向。据中国信通院认证&#xff…