找回密码
 立即注册
首页 业界区 业界 React 基础核心概念(8 个)——从入门到能写业务组件( ...

React 基础核心概念(8 个)——从入门到能写业务组件(上)| 葡萄城技术团队

蓟晓彤 7 天前
React 基础核心概念(8 个)——从入门到能写业务组件(上)

前言:为什么要先掌握这些基础概念?

对国内开发者来说,React 是开发中后台系统、电商前端、移动端 H5 的“刚需技能”。但很多人刚学就陷入“会写 JSX 却不懂原理”的困境——比如不知道为什么状态更新后页面不刷新,或者写组件时反复遇到“属性透传”的麻烦。
这篇整理的 8 个基础概念,是 React 开发的“地基”:从 JSX 语法到最常用的 Hooks,每个都配了国内项目常见的示例(比如商品列表渲染、用户登录状态管理),帮你跳过“照抄代码却不懂逻辑”的坑,真正能独立写业务组件。
1. 什么是 React 中的 JSX?搞懂 React 专属语法

定义与作用

JSX(JavaScript XML)是 React 的“模板语法”,允许你在 JS 代码里写类似 HTML 的结构。很多初学者以为它是“HTML 的变体”,其实它最终会被 Babel 编译成React.createElement()函数,生成 React 元素(虚拟 DOM 节点)。
国内开发场景中,JSX 是写组件的“标配”——无论是电商的商品卡片,还是后台的表格组件,都靠 JSX 描述 UI 结构。
国内项目示例:电商商品卡片(JSX 实战)
  1. import React from 'react';
  2. // 引入国内常用的UI组件库(如Ant Design)
  3. import { Card, Button, Tag } from 'antd';
  4. // 商品卡片组件:接收商品数据作为props
  5. const ProductCard = ({ product }) => {
  6.   const { id, name, price, stock, isDiscount } = product;
  7.   return (
  8.     // JSX支持嵌入JS表达式(用{}包裹)
  9.     <card key="{id}" title="{name}" cover="{<img" src="https://www.cnblogs.com/{`/images/products/${id}.jpg`}" alt="{name}" />}
  10.       style={{ width: 240, margin: '16px' }} // 行内样式需用对象(驼峰命名)
  11.     >
  12.       {/* 条件渲染标签:有折扣显示“限时折扣” */}
  13.       {isDiscount && <tag color="red">限时折扣</tag>}
  14.       
  15.         ¥{price.toFixed(2)}
  16.         库存:{stock}件
  17.       
  18.       {/* 事件绑定:点击按钮添加购物车(后续会讲事件处理) */}
  19.       <button type="primary" danger  width: '100%', margintop: 12 }} onclick="{()" => console.log(`添加商品 ${name} 到购物车`)}
  20.       >
  21.         加入购物车
  22.       </button>
  23.    
  24.   );
  25. };
  26. // 使用组件:传入国内电商常见的商品数据
  27. const ProductList = () => {
  28.   const products = [
  29.     { id: 1, name: '华为Mate 60 Pro', price: 6999, stock: 120, isDiscount: false },
  30.     { id: 2, name: '小米14', price: 4999, stock: 86, isDiscount: true },
  31.   ];
  32.   return (
  33.    
  34.       {products.map(product => <productcard product="{product}" />)}
  35.    
  36.   );
  37. };
  38. export default ProductList;
复制代码
注意点(国内开发者常踩的坑)


  • 不能直接写class:需用className(因为class是 JS 关键字);
  • 自闭合标签必须写/:比如
    1.jpg
    ,不像 HTML 里可以省略;
  • 只能有一个根节点:如果有多个元素,需用或(简写<>)包裹。
2. React 中的 State 与 Props:组件的“数据传递与状态管理”核心

定义与区别


  • Props(属性):父组件传给子组件的数据,类似“函数参数”,只读不可改(子组件不能直接修改 props);
  • State(状态):组件内部管理的“动态数据”(如输入框内容、弹窗显示/隐藏),可修改但需用 setter 方法(如setCount),修改后会触发组件重新渲染。
国内开发中,这两者是“父子组件通信”和“组件内部状态控制”的核心——比如后台管理系统中,父组件传“表格数据”给子表格组件(用 props),子组件内部管理“分页页码”(用 state)。
国内项目示例:后台表格组件(State 与 Props 结合)
  1. import React, { useState } from 'react';
  2. import { Table, Pagination } from 'antd';
  3. // 子组件:表格(接收父组件传的props)
  4. const DataTable = ({ tableData, columns }) => {
  5.   // 子组件内部状态:当前页码(只能自己修改)
  6.   const [currentPage, setCurrentPage] = useState(1);
  7.   // 每页条数(国内后台常用10/20/50条)
  8.   const pageSize = 10;
  9.   // 处理页码变化(子组件内部更新state)
  10.   const handlePageChange = (page) => {
  11.     setCurrentPage(page);
  12.   };
  13.   // 分页逻辑:截取当前页数据
  14.   const currentData = tableData.slice(
  15.     (currentPage - 1) * pageSize,
  16.     currentPage * pageSize
  17.   );
  18.   return (
  19.    
  20.       {/* 表格:用props传的columns和处理后的currentData */}
  21.       <table columns="{columns}" dataSource="{currentData}" rowKey="id" pagination="{false}" 关闭表格自带分页,用自定义分页></table>
  22.       {/* 分页组件:状态currentPage控制显示 */}
  23.       <pagination current="{currentPage}" pageSize="{pageSize}" total="{tableData.length}" onChange="{handlePageChange}"  marginTop: 16, textAlign: 'right' }} />
  24.    
  25.   );
  26. };
  27. // 父组件:使用表格(传props给子组件)
  28. const UserManagePage = () => {
  29.   // 父组件数据:用户列表(模拟接口返回的国内后台数据)
  30.   const userColumns = [
  31.     { title: '用户ID', dataIndex: 'id', key: 'id' },
  32.     { title: '用户名', dataIndex: 'username', key: 'username' },
  33.     { title: '角色', dataIndex: 'role', key: 'role' },
  34.     { title: '状态', dataIndex: 'status', key: 'status', render: (status) => status ? '启用' : '禁用' },
  35.   ];
  36.   const userData = [
  37.     { id: 1, username: 'zhangsan', role: '管理员', status: true },
  38.     { id: 2, username: 'lisi', role: '普通用户', status: true },
  39.     // ... 更多数据
  40.   ];
  41.   // 父组件传给子组件的props:tableData和columns
  42.   return <datatable tableData="{userData}" columns="{userColumns}" />;
  43. };
  44. export default UserManagePage;
复制代码
3. React 事件处理:和原生 JS 有啥不一样?

核心特点

React 的“合成事件”(SyntheticEvent)是对原生 DOM 事件的封装,目的是解决“跨浏览器兼容”问题——国内开发者不用再写addEventListener兼容 IE,直接用onClick这类驼峰命名的事件即可。
另外,React 事件处理有两个关键点:

  • 事件处理函数需要“正确绑定 this”(类组件中常见,函数组件用箭头函数可避免);
  • 传参时需用“函数包裹”(如onClick={() => handleDelete(id)}),避免直接执行函数。
国内项目示例:表单提交与按钮点击(高频场景)
  1. import React, { useState } from 'react';
  2. import { Form, Input, Button, message } from 'antd';
  3. const LoginForm = () => {
  4.   const [loading, setLoading] = useState(false); // 登录加载状态
  5.   // 1. 表单提交事件(带参数,需用箭头函数包裹)
  6.   const handleSubmit = async (values) => {
  7.     setLoading(true); // 点击提交后显示加载状态
  8.     try {
  9.       // 模拟国内接口请求(如调用后端登录接口)
  10.       const res = await fetch('/api/login', {
  11.         method: 'POST',
  12.         headers: { 'Content-Type': 'application/json' },
  13.         body: JSON.stringify(values),
  14.       });
  15.       const data = await res.json();
  16.       if (data.success) {
  17.         message.success('登录成功!');
  18.         // 跳转到首页(国内常用react-router)
  19.         // navigate('/home');
  20.       } else {
  21.         message.error(data.message || '登录失败');
  22.       }
  23.     } catch (error) {
  24.       message.error('网络错误,请重试');
  25.     } finally {
  26.       setLoading(false); // 无论成功失败,关闭加载状态
  27.     }
  28.   };
  29.   // 2. 普通按钮点击事件(无参数)
  30.   const handleReset = () => {
  31.     // 重置表单(Ant Design Form方法)
  32.     Form.useForm()[0].resetFields();
  33.   };
  34.   return (
  35.     <form name="login_form" layout="vertical" onFinish="{handleSubmit}" 表单提交事件(React合成事件)  width: 350, margin: '0 auto' }}>
  36.       <form.item name="username" label="用户名" rules="{[{" required: true, message: '请输入用户名' }]}>
  37.         <input placeholder="请输入用户名">
  38.       </form.item>
  39.       <form.item name="password" label="密码" rules="{[{" required: true, message: '请输入密码' }]}>
  40.         <input.password placeholder="请输入密码" />
  41.       </form.item>
  42.       <form.item>
  43.         <button type="primary" htmltype="submit" loading="{loading}"  marginright: 8 }}>
  44.           登录
  45.         </button>
  46.         <button onclick="{handleReset}">重置</button>
  47.       </form.item>
  48.     </form>
  49.   );
  50. };
  51. export default LoginForm;
复制代码
4. React 条件渲染:怎么优雅地控制 UI 显示?

核心场景

国内开发中,条件渲染几乎无处不在:用户登录/未登录显示不同按钮、接口请求中显示“加载中”、数据为空显示“暂无数据”……React 没有专门的“条件渲染语法”,而是用 JS 的逻辑(如if-else、三元运算符、&&)实现。
国内项目示例:多场景条件渲染(覆盖高频需求)

[code]import React, { useState, useEffect } from 'react';import { Spin, Empty, List, Avatar } from 'antd';const MessageList = () => {  // 状态:加载中、消息数据、是否登录  const [loading, setLoading] = useState(true);  const [messages, setMessages] = useState([]);  const [isLogin, setIsLogin] = useState(false);  // 模拟接口请求(国内后台常见的“消息列表”接口)  useEffect(() => {    const fetchMessages = async () => {      try {        const res = await fetch('/api/messages');        const data = await res.json();        setMessages(data.list);        setIsLogin(data.isLogin); // 接口返回登录状态      } catch (error) {        console.error('获取消息失败:', error);      } finally {        setLoading(false);      }    };    fetchMessages();  }, []);  // 1. 加载中:显示Spin组件(国内常用加载组件)  if (loading) {    return ;  }  // 2. 未登录:显示“请登录”提示(三元运算符)  if (!isLogin) {    return (              请先登录查看消息

         setIsLogin(true)}>          立即登录                  );  }  return (          我的消息

      {/* 3. 有消息:渲染列表(&& 语法) */}      {messages.length > 0 ? (         (
您需要登录后才可以回帖 登录 | 立即注册