尧图建网站 尧图建网站 YAOTU WEB BUILD 免费咨询
ARTICLE DETAIL

资讯详情

深耕网站建设与建站编程的一线实战洞察。

从ROS 2仿真到具身智能:拆解家用机器人核心技术栈与开发实战

从ROS 2仿真到具身智能:拆解家用机器人核心技术栈与开发实战 如果你最近关注科技新闻可能会注意到一个有趣的现象一边是社交媒体上关于家用机器人的讨论热度不减另一边却是普通消费者面对动辄数万元的产品望而却步。一个核心的矛盾摆在我们面前为什么用户普遍觉得“不实用”、“太贵”而资本市场却依然在疯狂下注甚至将其视为下一个“iPhone时刻”这背后赌的绝不仅仅是一个能扫地或端茶倒水的“高级家电”。资本看到的是一个正在从“功能机”向“智能机”跃迁的赛道其核心价值在于“通用移动智能体”General-Purpose Mobile Manipulator的雏形。今天这篇文章我们不谈虚的就从技术演进的底层逻辑、当前产品的真实能力拆解以及开发者如何切入这个生态来彻底讲清楚家用机器人这场赌局到底在赌什么作为技术人员我们又该如何理解并参与其中你会发现真正的机会不在于购买一个成品机器人而在于理解其背后的技术栈——从多模态感知、具身智能到操作系统——并找到你能够贡献代码或创意的位置。1. 从“功能执行”到“场景理解”家用机器人的价值跃迁要理解资本的逻辑首先要跳出“机器人高级玩具”的固有认知。过去十年的家用机器人以扫地机器人为代表本质是“预设环境的自动执行器”。它们依赖激光雷达Lidar构建静态地图按照编好的算法路径行走完成单一、明确的指令如清扫。其智能上限受限于预先建模的环境。而新一代家用机器人如Figure 01、斯坦福的Mobile ALOHA、特斯拉的Optimus原型的目标是成为“非结构化环境的通用任务执行者”。这其中的技术代差主要体现在三个维度感知维度从“激光雷达视觉避障”升级为“多模态大模型LMM驱动的场景理解”。机器人不仅能“看到”物体还能理解“这是一个打翻的牛奶盒”、“那是一把需要抓握的壶柄”并推断出物体属性和潜在用途。决策维度从“基于规则的路径规划”升级为“基于大语言模型LLM的任务拆解与规划”。你无需说“向前走1米左转30度伸出机械臂抓取”而只需说“帮我清理一下洒在桌上的咖啡”。LLM会将这个模糊指令拆解成一系列可执行的原子动作。控制维度从“精确的轨迹控制”升级为“模仿学习与强化学习结合的柔性操作”。机器人通过观看人类演示模仿学习并在虚拟或真实环境中不断试错强化学习学会像人一样处理力度、角度和应对不确定性比如拧瓶盖、折叠衣服。资本下注的正是这三大技术维度在“家庭”这个最复杂非结构化场景中实现融合与产品化的可能性。赌的是“具身智能”Embodied AI从实验室走向客厅的拐点。虽然当前产品笨拙、昂贵但技术路径已经清晰一旦在数据、算法和成本上取得突破其市场空间将是指数级增长。2. 核心技术栈拆解一台现代家用机器人由什么构成对于开发者而言理解其技术栈是参与的第一步。一个典型的现代家用机器人软件系统可以粗略分为以下五层层级名称核心功能关键技术/组件举例应用层任务与技能面向用户的具体功能如“备餐”、“收纳”技能市场、工作流引擎、自然语言交互决策层大脑AI模型理解指令、规划任务、处理异常大语言模型LLM、视觉语言模型VLM、世界模型协调层机器人操作系统硬件资源管理、任务调度、通信中间件ROS 2、Isaac Sim仿真、厂商自研OS感知层感官系统环境与自身状态感知深度相机、激光雷达、IMU、麦克风阵列、触觉传感器执行层身体硬件驱动执行具体动作电机伺服驱动、机械臂逆运动学求解、步态控制其中最值得开发者关注的是“协调层”和“决策层”因为它们是软件定义机器人能力的关键。协调层以ROS 2为例它是机器人的“中枢神经系统”。所有传感器数据、决策指令、控制命令都通过它进行发布、订阅和传递。理解ROS 2的节点Node、话题Topic、服务Service和动作Action通信模型是进行机器人软件开发的基础。决策层AI模型集成这是当前创新的主战场。机器人如何将“我渴了”这句话变成“走到冰箱前-打开门-取出水瓶-拧开盖子-倒入杯子”这一系列动作这依赖于LLMVLM的协同工作。3. 环境准备搭建你的第一个机器人仿真开发环境在真机成本高昂的现状下仿真Simulation是绝大多数开发者和研究人员入门机器人学的必经之路。我们将使用最流行的ROS 2和Gazebo仿真器创建一个简单的移动机器人模型并让其完成最基本的导航任务。前置条件操作系统Ubuntu 22.04 LTS推荐对ROS 2支持最好内存至少8GB磁盘空间至少20GB可用空间步骤1安装ROS 2 Humble Hawksbill打开终端依次执行以下命令# 1. 设置语言环境确保支持UTF-8 sudo apt update sudo apt install locales sudo locale-gen en_US en_US.UTF-8 sudo update-locale LC_ALLen_US.UTF-8 LANGen_US.UTF-8 export LANGen_US.UTF-8 # 2. 添加ROS 2软件源 sudo apt install software-properties-common sudo add-apt-repository universe sudo apt update sudo apt install curl -y sudo curl -sSL https://raw.githubusercontent.com/ros/rosdistro/master/ros.key -o /usr/share/keyrings/ros-archive-keyring.gpg echo deb [arch$(dpkg --print-architecture) signed-by/usr/share/keyrings/ros-archive-keyring.gpg] http://packages.ros.org/ros2/ubuntu $(. /etc/os-release echo $UBUNTU_CODENAME) main | sudo tee /etc/apt/sources.list.d/ros2.list /dev/null # 3. 安装ROS 2桌面版包含ROS、RViz、Gazebo等工具 sudo apt update sudo apt install ros-humble-desktop -y # 4. 设置环境变量每次打开新终端都需要执行或将其加入~/.bashrc source /opt/ros/humble/setup.bash echo source /opt/ros/humble/setup.bash ~/.bashrc步骤2安装Gazebo Fortress或经典版Gazebo是物理仿真引擎。ROS Humble默认集成了Gazebo的经典版本但为了更好的性能可以安装更新的Fortress版本。# 安装Gazebo Fortress sudo apt install wget sudo wget https://packages.osrfoundation.org/gazebo.gpg -O /usr/share/keyrings/pkgs-osrf-archive-keyring.gpg echo deb [arch$(dpkg --print-architecture) signed-by/usr/share/keyrings/pkgs-osrf-archive-keyring.gpg] http://packages.osrfoundation.org/gazebo/ubuntu-stable $(lsb_release -cs) main | sudo tee /etc/apt/sources.list.d/gazebo-stable.list /dev/null sudo apt update sudo apt install gazebo-fortress -y # 安装ROS与Gazebo的桥梁包 sudo apt install ros-humble-gazebo-ros-pkgs -y至此一个基础的机器人仿真开发环境就搭建完成了。4. 创建并仿真一个简单的移动机器人模型我们将创建一个带有激光雷达的差分驱动小车模型并在Gazebo中加载一个室内环境让小车实现自主避障。步骤1创建一个ROS 2工作空间和功能包# 创建工作空间目录 mkdir -p ~/robot_ws/src cd ~/robot_ws/src # 创建一个新的功能包依赖包括 gazebo_ros 和 rclpy ros2 pkg create my_first_robot --build-type ament_python --dependencies rclpy gazebo_ros cd my_first_robot步骤2创建机器人URDF模型文件URDF是描述机器人外观和物理属性的XML格式文件。在my_first_robot目录下创建urdf文件夹并新建robot.urdf.xacro文件使用xacro宏以简化编写?xml version1.0? robot xmlns:xacrohttp://www.ros.org/wiki/xacro namesimple_robot !-- 定义常量 -- xacro:property namebase_length value0.4 / xacro:property namebase_width value0.3 / xacro:property namebase_height value0.2 / xacro:property namewheel_radius value0.05 / xacro:property namewheel_width value0.02 / !-- 基础连杆车身 -- link namebase_link visual geometry box size${base_length} ${base_width} ${base_height}/ /geometry material nameblue color rgba0 0.2 0.8 1/ /material /visual collision geometry box size${base_length} ${base_width} ${base_height}/ /geometry /collision inertial mass value5.0/ inertia ixx0.1 ixy0.0 ixz0.0 iyy0.1 iyz0.0 izz0.1/ /inertial /link !-- 左轮 -- link nameleft_wheel visual geometry cylinder radius${wheel_radius} length${wheel_width}/ /geometry material nameblack color rgba0.1 0.1 0.1 1/ /material /visual collision geometry cylinder radius${wheel_radius} length${wheel_width}/ /geometry /collision inertial mass value0.5/ inertia ixx0.001 ixy0.0 ixz0.0 iyy0.001 iyz0.0 izz0.001/ /inertial /link !-- 右轮与左轮对称 -- xacro:macro namewheel paramsprefix reflect joint name${prefix}_wheel_joint typecontinuous parent linkbase_link/ child link${prefix}_wheel/ origin xyz0 ${reflect*base_width/2} -${base_height/2-wheel_radius} rpy${reflect*pi/2} 0 0/ axis xyz0 1 0/ /joint link name${prefix}_wheel visual geometry cylinder radius${wheel_radius} length${wheel_width}/ /geometry material nameblack/ /visual collision geometry cylinder radius${wheel_radius} length${wheel_width}/ /geometry /collision inertial mass value0.5/ inertia ixx0.001 ixy0.0 ixz0.0 iyy0.001 iyz0.0 izz0.001/ /inertial /link /xacro:macro xacro:wheel prefixleft reflect1/ xacro:wheel prefixright reflect-1/ !-- 激光雷达模拟 -- link namelaser_link visual geometry cylinder radius0.03 length0.05/ /geometry material namered color rgba0.8 0.1 0.1 1/ /material /visual /link joint namelaser_joint typefixed parent linkbase_link/ child linklaser_link/ origin xyz0 0 ${base_height/20.03} rpy0 0 0/ /joint gazebo referencelaser_link sensor typeray namelaser_sensor pose0 0 0 0 0 0/pose visualizetrue/visualize update_rate10/update_rate ray scan horizontal samples360/samples resolution1/resolution min_angle-3.14159/min_angle max_angle3.14159/max_angle /horizontal /scan range min0.1/min max10.0/max resolution0.01/resolution /range /ray plugin namegazebo_ros_laser_controller filenamelibgazebo_ros_ray_sensor.so ros namespace//namespace argument~/out:scan/argument /ros output_typesensor_msgs/LaserScan/output_type frame_namelaser_link/frame_name /plugin /sensor /gazebo !-- 差分驱动控制器插件 -- gazebo plugin namedifferential_drive_controller filenamelibgazebo_ros_diff_drive.so ros namespace//namespace /ros update_rate30/update_rate left_jointleft_wheel_joint/left_joint right_jointright_wheel_joint/right_joint wheel_separation${base_width}/wheel_separation wheel_diameter${2*wheel_radius}/wheel_diameter max_wheel_torque20/max_wheel_torque max_wheel_acceleration1.0/max_wheel_acceleration command_topiccmd_vel/command_topic odometry_topicodom/odometry_topic odometry_frameodom/odometry_frame robot_base_framebase_link/robot_base_frame publish_odomtrue/publish_odom publish_odom_tftrue/publish_odom_tf publish_wheel_tftrue/publish_wheel_tf /plugin /gazebo /robot步骤3创建启动文件在Gazebo中生成世界并加载机器人在功能包目录下创建launch文件夹并新建simulate_robot.launch.py文件# 文件路径my_first_robot/launch/simulate_robot.launch.py import os from ament_index_python.packages import get_package_share_directory from launch import LaunchDescription from launch.actions import IncludeLaunchDescription from launch.launch_description_sources import PythonLaunchDescriptionSource from launch.substitutions import LaunchConfiguration from launch_ros.actions import Node def generate_launch_description(): # 获取功能包路径 pkg_path get_package_share_directory(my_first_robot) urdf_file os.path.join(pkg_path, urdf, robot.urdf.xacro) # 启动Gazebo空世界 gazebo_launch IncludeLaunchDescription( PythonLaunchDescriptionSource([ os.path.join(get_package_share_directory(gazebo_ros), launch, gazebo.launch.py) ]), launch_arguments{world: os.path.join(pkg_path, worlds, empty.world)}.items() ) # 将URDF文件上传到参数服务器 robot_state_publisher Node( packagerobot_state_publisher, executablerobot_state_publisher, namerobot_state_publisher, outputscreen, arguments[urdf_file], parameters[{use_sim_time: True}] ) # 在Gazebo中生成机器人模型 spawn_entity Node( packagegazebo_ros, executablespawn_entity.py, arguments[-entity, simple_robot, -file, urdf_file, -x, 0, -y, 0, -z, 0.1], outputscreen ) # 启动一个节点发布简单的控制指令让机器人转圈 circle_driver Node( packagemy_first_robot, executablecircle_driver, outputscreen ) return LaunchDescription([ gazebo_launch, robot_state_publisher, spawn_entity, circle_driver, ])步骤4编写一个简单的控制节点在功能包目录下的my_first_robot文件夹内与resource和test同级新建circle_driver.py文件# 文件路径my_first_robot/my_first_robot/circle_driver.py import rclpy from rclpy.node import Node from geometry_msgs.msg import Twist class CircleDriver(Node): def __init__(self): super().__init__(circle_driver) self.publisher_ self.create_publisher(Twist, cmd_vel, 10) timer_period 0.1 # 0.1秒发布一次指令 self.timer self.create_timer(timer_period, self.timer_callback) self.get_logger().info(Circle driver node started, robot will move in a circle.) def timer_callback(self): msg Twist() msg.linear.x 0.2 # 前进速度 0.2 m/s msg.angular.z 0.5 # 旋转速度 0.5 rad/s形成圆周运动 self.publisher_.publish(msg) def main(argsNone): rclpy.init(argsargs) circle_driver CircleDriver() rclpy.spin(circle_driver) circle_driver.destroy_node() rclpy.shutdown() if __name__ __main__: main()步骤5修改setup.py确保节点可执行编辑setup.py文件在console_scripts括号内添加入口点# 文件路径my_first_robot/setup.py from setuptools import setup package_name my_first_robot setup( namepackage_name, version0.0.0, packages[package_name], data_files[ (share/ament_index/resource_index/packages, [resource/ package_name]), (share/ package_name, [package.xml]), (share/ package_name /urdf, [urdf/robot.urdf.xacro]), (share/ package_name /launch, [launch/simulate_robot.launch.py]), (share/ package_name /worlds, [worlds/empty.world]), ], install_requires[setuptools], zip_safeTrue, maintaineryour_name, maintainer_emailyour_emailexample.com, descriptionA simple robot simulation package, licenseApache-2.0, tests_require[pytest], entry_points{ console_scripts: [ circle_driver my_first_robot.circle_driver:main, # 添加这一行 ], }, )步骤6编译并运行回到工作空间根目录进行编译并运行仿真cd ~/robot_ws colcon build --packages-select my_first_robot source install/setup.bash ros2 launch my_first_robot simulate_robot.launch.py5. 运行结果与效果验证执行上述启动命令后Gazebo客户端和RViz如果安装了会自动打开。你应该能看到以下现象Gazebo窗口一个空旷的灰色世界中央出现了一个蓝色长方体车身带着两个黑色轮子和一个红色圆柱体激光雷达的机器人。机器人运动几秒钟后机器人开始以圆周轨迹运动。这是因为circle_driver节点在持续发布线速度和角速度指令。话题数据打开一个新的终端输入以下命令可以查看机器人发布的数据# 查看所有活跃的话题 ros2 topic list # 你应该能看到 /cmd_vel, /odom, /scan 等话题 # 实时查看激光雷达扫描数据 ros2 topic echo /scan --no-arr # 查看里程计信息 ros2 topic echo /odom如何验证成功基础验证Gazebo中机器人按圆形运动。传感器验证/scan话题持续输出数据表示激光雷达仿真正常工作。控制验证你可以通过命令行手动发布速度指令来覆盖圆周运动测试机器人的响应ros2 topic pub -r 10 /cmd_vel geometry_msgs/msg/Twist {linear: {x: 0.5, y: 0.0, z: 0.0}, angular: {x: 0.0, y: 0.0, z: 0.0}}这条命令会让机器人以0.5m/s的速度直线前进。按CtrlC停止。至此你已经完成了一个最基础的“机器人”从建模、仿真到控制的完整流程。它虽然简单但涵盖了现代机器人开发的核心环节描述URDF、仿真Gazebo、控制ROS 2节点、感知模拟激光雷达。6. 从仿真到真实挑战当前家用机器人的核心瓶颈通过上面的仿真我们获得了一个可控的机器人。但为什么真实的家庭服务机器人依然步履维艰仿真与现实的“鸿沟”Sim2Real Gap和成本是两大拦路虎。1. 感知与理解的鸿沟仿真环境物体是规则的、物理想象是理想的、光线是均匀的。我们的URDF模型是精确的。真实家庭光线明暗变化、物体随意摆放、表面反光、宠物突然闯入、地面有散落的玩具。任何未经训练的异常都会导致感知失败。当前技术瓶颈不在于“看到”而在于“看懂”并“预测”。例如识别一个“半透明塑料袋”和“一团电线”对机器人视觉仍是巨大挑战。2. 操控的精度与安全仿真中机械臂可以完美抓取我们定义好的物体。现实中抓取一个鸡蛋、一件柔软的T恤、一个光滑的玻璃杯需要毫米级的力控和复杂的材料形变建模。用力过大会捏碎鸡蛋过轻会抓不住杯子。这需要昂贵的力/触觉传感器和先进的算法成本极高。3. 长尾任务与常识推理“把客厅收拾一下”这种指令对人类来说包含大量隐含常识什么是“收拾”什么东西该放回哪里遇到不认识的物品怎么办机器人需要庞大的常识知识库和强大的推理能力这正是当前大模型试图解决的问题但离稳定、可靠的产品化还有距离。4. 成本与功耗实现上述能力所需的算力高性能GPU、传感器高精度激光雷达、深度相机、力传感器和精密执行器机械臂、灵巧手使得单台机器人的BOM成本难以降到消费级水平。7. 开发者如何切入生态位与技能栈建议面对高昂的硬件成本个人开发者并非无能为力。资本的涌入正在催生一个庞大的软件与算法生态。你可以从以下几个层面切入1. 算法层在仿真中训练与验证技能栈Python, PyTorch/TensorFlow, ROS 2, Gazebo/Isaac Sim, OpenAI Gym/RLlib。做什么研究并复现前沿的强化学习RL、模仿学习IL算法。在仿真环境中训练机器人完成特定任务如开门、抓取特定物体。你的成果可以是以Docker容器或ROS 2功能包形式开源的算法模型。学习路径精通ROS 2通信和工具链。学习使用MoveIt2机械臂运动规划和Navigation2移动导航。深入研究Gazebo或NVIDIA Isaac Sim的API编写复杂的环境。掌握 Stable Baselines3 等RL库训练你的第一个仿真智能体。2. 技能层构建可复用的任务模块技能栈Python, ROS 2 (Action/Service), 状态机如SMACH可能涉及计算机视觉库OpenCV, PyTorch。做什么将“泡咖啡”、“叠衣服”等复杂任务拆解并编码成可配置、可组合的“技能”Skill。例如一个“倒水”技能可能包括“寻找水壶”、“抓握壶柄”、“移动到杯子上方”、“倾斜壶身”等子动作。你可以开发并开源这些技能包。示例伪代码逻辑# 一个简单的“移动到某物体前”技能框架 class NavigateToObjectSkill: def __init__(self, object_name): self.object_name object_name self.nav_client ActionClient(NavigateToPose, navigate_to_pose) def execute(self): # 1. 通过视觉服务识别物体位置 pose self.detect_object_pose(self.object_name) # 2. 规划并执行导航到该位置附近的点 goal_pose self.calculate_goal_near_object(pose) self.send_navigation_goal(goal_pose) # 3. 等待完成或处理失败 return self.wait_for_result()3. 决策层与大模型LLM/VLM集成技能栈Python, LangChain/Transformers Agents, ROS 2, API设计。做什么搭建一个“机器人大脑”服务。该服务接收用户的自然语言指令如“我渴了”调用LLM如GPT-4、Claude进行任务规划调用VLM如GPT-4V进行场景理解最终输出ROS 2的Action Goal序列。这是当前最热门的研究和创业方向。关键挑战如何将大模型抽象的“想法”安全、可靠地转化为机器人底层的控制指令并处理执行过程中的异常。4. 工具与基础设施层技能栈Docker/Kubernetes, CI/CD, 数据管理Web前端。做什么开发机器人仿真云平台、数据标注与管理工具、技能市场、机器人远程监控与诊断系统。这些是支撑整个生态运转的“水电煤”。8. 常见问题与排查思路ROS 2 Gazebo 实战在开发过程中你会遇到各种问题。以下是一些典型问题及排查思路问题现象可能原因排查方式解决方案ros2 launch后 Gazebo 黑屏或卡住1. 显卡驱动问题2. Gazebo 模型下载失败1. 在终端运行gazebo --verbose查看详细日志。2. 检查~/.gazebo文件夹权限和磁盘空间。1. 安装推荐显卡驱动使用--verbose模式启动。2. 手动下载模型包并放置到~/.gazebo/models/。机器人模型在 Gazebo 中“抖动”或“下坠”1. URDF 中惯性Inertial参数设置错误或缺失。2. 碰撞Collision和视觉Visual模型不匹配。1. 检查URDF中每个link是否都包含正确的inertial标签。2. 在Gazebo中开启“视图-碰撞”查看碰撞模型。1. 为所有连杆link添加合理的质量和惯性矩阵。2. 确保碰撞模型是视觉模型的简化凸包。激光雷达/scan话题没有数据1. Gazebo插件配置错误。2. 传感器命名空间或话题名冲突。1.ros2 topic list查看是否有/scan。2.ros2 topic info /scan查看发布者。3. 检查URDF中plugin的frame_name和话题名。1. 确保plugin的filename正确如libgazebo_ros_ray_sensor.so。2. 确保frame_name与雷达link名称一致。控制指令/cmd_vel发布后机器人不动1. 差分驱动插件参数错误如关节名、轮间距。2. 机器人模型与地面接触问题。1.ros2 topic echo /cmd_vel确认指令已发布。2. 检查Gazebo左下角的实时信息看是否有错误提示。3. 检查差分驱动插件中left_joint和right_joint名称是否与URDF完全一致。1. 仔细核对插件参数与URDF模型中的关节名、尺寸。2. 在URDF中为车轮添加gazebo标签定义摩擦系数等物理属性。RViz 中看不到机器人模型1.robot_state_publisher节点未运行或出错。2. TF 树不完整或错误。1.ros2 node list确认节点在运行。2.ros2 run tf2_tools view_frames.py生成TF树PDF检查连接关系。3. 在RViz中添加“RobotModel”显示类型并检查“Fixed Frame”设置。1. 确保启动文件正确启动了robot_state_publisher节点并传入了正确的URDF文件路径。2. 确保URDF中所有关节joint的父子link关系正确。9. 最佳实践与工程建议如果你想严肃地进入机器人开发领域以下建议能帮你避开很多坑版本管理是生命线使用Git管理你的URDF、Launch文件和代码。对于复杂的模型和场景考虑使用git lfs管理大型文件如3D模型。仿真优先持续集成任何算法或控制逻辑先在仿真中充分测试。尝试搭建CI流水线自动在仿真中运行测试确保代码变更不会破坏基础功能。模块化与接口标准化将你的系统拆分为独立的、功能单一的节点或技能。使用ROS 2的接口话题、服务、动作进行通信并编写清晰的接口文档。这有利于团队协作和代码复用。重视日志与可视化合理使用rclpy的日志级别DEBUG, INFO, WARN, ERROR。充分利用RViz2的强大可视化能力来调试感知、规划、控制等环节。数据可视化是理解机器人“在想什么”的关键。安全第一在仿真中可以大胆试错。但任何涉及真实机器人的操作必须设置“急停”开关并在低速、受限的环境下开始测试。永远假设你的代码会有bug硬件会出故障。拥抱社区与开源ROS 2和Gazebo有极其活跃的社区。遇到问题时优先在ROS Answers、GitHub Issues和Discourse论坛搜索。积极贡献你的代码和问题解决方案这是最快的学习方式。家用机器人这场“赌局”赌的是通用人工智能在物理世界的载体能否成功。对于用户它目前可能还是一个昂贵的新奇玩具但对于开发者和研究者它已经是一个充满挑战与机遇的、软硬件深度结合的黄金赛道。你不必等待一个完美的消费级产品从今天开始在仿真环境中构建你的第一个机器人技能理解从指令到动作的完整链条就是参与这场变革最好的方式。技术的突破往往来自于无数个简单模块的叠加与优化而你写的下一行代码或许就是其中一块关键的拼图。
返回列表