Mbed OS下BLE HID设备开发实战指南

news2026/3/24 20:48:16
1. 项目概述Mbed BLE HID 是一个面向嵌入式平台的轻量级蓝牙低功耗BLE人机接口设备HID实现库专为基于 ARM Mbed OS 的硬件平台设计核心验证目标平台为 Arduino Nano 33 BLE搭载 nRF52840 SoC。该库严格遵循 Bluetooth SIG 官方规范完整实现HID Over GATT Profile (HOGP)使微控制器能够以标准 BLE HID 设备身份被主流操作系统识别和使用——包括 GNU/LinuxBlueZ 5.50、Android 8.0、iOS 13 及 Windows 101809无需额外驱动或私有协议栈。与传统 USB HID 不同BLE HID 通过 GATTGeneric Attribute Profile服务结构暴露设备能力。Mbed BLE HID 并非简单封装底层 BLE API而是构建了一套分层抽象模型底层依托 Mbed OS 的BLE类与GattServer接口中层封装标准化的 Device Information ServiceDIS、Battery ServiceBAS及可扩展的HIDService基类上层提供开箱即用的HIDMouseService、HIDKeyboardService和HIDGamepadService三个具体实现。这种设计既保证了与标准 HID 协议栈的完全兼容性又为开发者提供了高度可定制的扩展路径。工程实践中该库的价值在于将复杂的 HID 报告描述符Report Descriptor、GATT 特征值Characteristic权限配置、连接状态管理、报告发送时序等细节封装为简洁的 C 接口。开发者无需深入理解 USB HID Usage Tables 或 BLE ATT 层协议细节即可在数分钟内让一块 Nano 33 BLE 变身为无线鼠标、键盘或游戏手柄并直接接入现有操作系统生态。2. 系统架构与核心组件2.1 整体分层架构Mbed BLE HID 采用清晰的三层架构层级组件职责关键依赖应用层Nano33BleHIDT模板类、MbedBleHID基类提供设备初始化、事件循环启动、服务获取等顶层 API管理设备名称、外观Appearance等元数据std::shared_ptrHIDService、BLE实例服务层HIDService抽象基类、HIDMouseService、HIDKeyboardService、HIDGamepadService实现具体 HID 功能逻辑定义报告描述符处理输入数据到报告字节流的映射管理 GATT 特征值如 Report、Protocol Mode、Boot Keyboard Input ReportGattServer、HIDReportMap内部协议层DeviceInformationService、BatteryService、HOGP标准服务结构提供强制性 BLE 服务DIS 包含 Manufacturer Name、Model Number 等字段BAS 提供电池电量读取HOGP 定义 HID Information、HID Control Point 等特征值Mbed OSBLE类、GattCharacteristic所有服务均通过BLE::init()初始化的单例BLE对象注册到 GATT 服务器。HIDService的派生类在构造时自动注册其专属的 GATT 服务UUID:0x1812并声明必要的特征值Characteristics例如HID_REPORTUUID:0x2A4D用于传输 HID 报告数据属性为READ | WRITE_WITHOUT_RESPONSE | NOTIFYHID_PROTOCOL_MODEUUID:0x2A4E控制报告协议模式Report Mode 或 Boot Mode属性为READ | WRITEHID_INFORMATIONUUID:0x2A4A只读特征值包含 HID 规范版本、国家代码、标志位如远程唤醒支持2.2 关键数据结构HID 报告描述符Report DescriptorHID 报告描述符是整个 HID 协议的核心它是一段二进制字节序列由一系列“项”Items组成每个项以一个一字节的标签Tag开头后跟可变长度的数据。该描述符向主机如 PC精确声明了设备的输入/输出能力、数据格式、逻辑范围及物理单位。Mbed BLE HID 将此过程抽象为HIDReportMap类开发者通过调用其成员函数生成描述符。以HIDMouseService为例其默认报告描述符精简版如下// Mouse Report Descriptor (16 bytes) const uint8_t mouse_report_desc[] { 0x05, 0x01, // USAGE_PAGE (Generic Desktop) 0x09, 0x02, // USAGE (Mouse) 0xA1, 0x01, // COLLECTION (Application) 0x09, 0x01, // USAGE (Pointer) 0xA1, 0x00, // COLLECTION (Physical) 0x05, 0x09, // USAGE_PAGE (Button) 0x19, 0x01, // USAGE_MINIMUM (Button 1) 0x29, 0x03, // USAGE_MAXIMUM (Button 3) 0x15, 0x00, // LOGICAL_MINIMUM (0) 0x25, 0x01, // LOGICAL_MAXIMUM (1) 0x95, 0x03, // REPORT_COUNT (3) 0x75, 0x01, // REPORT_SIZE (1) 0x81, 0x02, // INPUT (Data,Var,Abs) 0x95, 0x01, // REPORT_COUNT (1) 0x75, 0x05, // REPORT_SIZE (5) 0x81, 0x03, // INPUT (Const,Var,Abs) 0x05, 0x01, // USAGE_PAGE (Generic Desktop) 0x09, 0x30, // USAGE (X) 0x09, 0x31, // USAGE (Y) 0x15, 0x81, // LOGICAL_MINIMUM (-127) 0x25, 0x7F, // LOGICAL_MAXIMUM (127) 0x75, 0x08, // REPORT_SIZE (8) 0x95, 0x02, // REPORT_COUNT (2) 0x81, 0x06, // INPUT (Data,Var,Rel) 0xC0, // END_COLLECTION 0xC0 // END_COLLECTION };此描述符声明了一个具有 3 个按钮左、右、中和 X/Y 轴相对位移的鼠标。REPORT_SIZE和REPORT_COUNT共同决定了报告的总长度此处为 4 字节3 bits for buttons 5 bits padding 2 * 8 bits for X/Y。HIDMouseService::motion(int8_t x, int8_t y)和HIDMouseService::button(uint8_t mask)函数正是将用户输入写入这个预分配的 4 字节缓冲区report_buffer[4]中。2.3 事件驱动模型与线程管理BLE 通信本质上是异步的。Mbed BLE HID 采用经典的事件驱动模型其核心是MbedBleHID_RunEventThread()函数。该函数创建一个独立的 RTOS 线程在 Mbed OS 下通常为osThreadNew并在其中运行一个无限循环持续调用BLE::processEvents()。此调用负责处理来自蓝牙控制器的底层事件如连接建立、断开、特征值写入请求触发已注册的回调函数如onConnection,onDisconnection,onDataWritten执行 GATT 服务器的内部状态更新对于HIDService最关键的回调是onDataWritten当主机向HID_PROTOCOL_MODE特征值写入数据时触发用于切换报告模式。而HIDService::SendReport()则是应用层主动发起的报告发送其内部调用GattServer::notify()向主机推送HID_REPORT特征值的当前值从而完成一次 HID 输入事件。3. 快速上手使用预置 HID 服务3.1 环境配置在 Arduino IDE 中需安装Arduino Mbed OS Boards包版本 ≥ 2.0.0。操作路径Tools Board Boards Manager...搜索 “mbed” 并安装。推荐使用 PlatformIO配合 Deviot 插件因其对 Mbed OS 项目的依赖管理和构建流程更为成熟。3.2 键盘示例详解以下代码展示了如何快速启用一个 BLE 键盘#include Nano33BleHID.h // 创建一个名为 My Keyboard 的 BLE 键盘实例 Nano33BleHIDHIDKeyboardService keyboard(My Keyboard); void setup() { // 初始化 BLE 子系统及 HID 服务 keyboard.initialize(); // 启动事件处理线程必须否则无响应 MbedBleHID_RunEventThread(); } void loop() { // 获取底层 HID 服务指针 auto* hid keyboard.hid(); // 发送字符串 Hello逐字符 const char* msg Hello; for (int i 0; msg[i] ! \0; i) { // 按下字符键自动处理 Shift 等修饰键 hid-pressKey(msg[i]); // 短暂延时模拟真实按键 ThisThread::sleep_for(100ms); // 释放按键 hid-releaseKey(); ThisThread::sleep_for(50ms); } // 长时间休眠避免高频轮询 ThisThread::sleep_for(5s); }HIDKeyboardService内部维护一个keylayouts.h文件定义了多种键盘布局如LAYOUT_US_INTERNATIONAL,LAYOUT_DE。其pressKey(char c)方法会根据当前布局查找字符对应的 USB HID 键码Key Code并将其写入报告缓冲区8 字节1 byte modifier 1 byte reserved 6 bytes key codes。例如按下 A 在 US 布局下对应键码0x04若同时按住 Shift则 modifier 字节为0x02。3.3 鼠标示例与硬件连接ble_mouse示例演示了如何将模拟摇杆转换为鼠标移动// 硬件连接 // 摇杆 X 轴 - A6 (ADC) // 摇杆 Y 轴 - A7 (ADC) // 摇杆按钮 - D2 (Digital) #include Nano33BleHID.h #include mbed.h Nano33BleHIDHIDMouseService mouse(Joystick Mouse); AnalogIn x_axis(A6); AnalogIn y_axis(A7); InterruptIn button(D2); void onButtonPress() { // 按下左键 mouse.hid()-button(HIDMouseService::LEFT_BUTTON); mouse.hid()-SendReport(); } void onButtonRelease() { // 释放所有按钮 mouse.hid()-button(0); mouse.hid()-SendReport(); } void setup() { mouse.initialize(); MbedBleHID_RunEventThread(); // 配置按钮中断 button.fall(onButtonPress); button.rise(onButtonRelease); } void loop() { // 读取摇杆模拟值0.0 - 1.0 float x_val x_axis.read(); float y_val y_axis.read(); // 映射到 -127 ~ 127 范围 int8_t x_motion (int8_t)((x_val - 0.5f) * 254.0f); int8_t y_motion (int8_t)((y_val - 0.5f) * 254.0f); // 发送鼠标移动报告 mouse.hid()-motion(x_motion, y_motion); mouse.hid()-SendReport(); ThisThread::sleep_for(20ms); // 控制报告频率 }此示例的关键在于motion()函数的参数范围。HIDMouseService的报告描述符将 X/Y 轴定义为LOGICAL_MINIMUM (-127)和LOGICAL_MAXIMUM (127)因此输入值必须严格在此范围内否则主机可能忽略或错误解析。4. 高级开发创建自定义 HID 服务4.1 继承HIDService的标准流程创建自定义 HID如一个带旋钮和 LED 指示灯的控制面板需继承HIDService并重写关键虚函数#include MbedBleHID.h #include HIDService.h class HIDControlPanelService : public HIDService { public: HIDControlPanelService(BLE _ble) : HIDService(_ble) { // 1. 构造报告描述符 buildReportDescriptor(); // 2. 注册 GATT 特征值 registerCharacteristics(); } // 必须重写返回设备在主机上的外观标识 ble::adv_data_appearance_t appearance() override { return ble::adv_data_appearance_t::GENERIC_HUMAN_INTERFACE_DEVICE; } // 可选重写处理来自主机的报告写入如 LED 控制命令 void onDataWritten(const GattWriteCallbackParams* params) override { if (params-handle led_control_char.getValueHandle()) { // 解析写入的字节控制 LED uint8_t led_state; led_control_char.read(led_state, sizeof(led_state)); setLED(led_state); } } private: // 自定义特征值用于主机向设备发送 LED 控制指令 GattCharacteristic led_control_char; void buildReportDescriptor() { // 使用 HIDReportMap 构建描述符 // 此处声明1 byte LED 状态Output1 byte 旋钮值Input1 byte 按钮Input report_map.clear(); report_map.addUsagePage(0x01); // Generic Desktop report_map.addUsage(0x09); // Button report_map.addCollection(0x01); // Application report_map.addUsage(0x30); // X (旋钮) report_map.addLogicalMin(0); report_map.addLogicalMax(255); report_map.addReportSize(8); report_map.addReportCount(1); report_map.addInput(0x02); // Data, Var, Abs report_map.addUsage(0x09); // Button report_map.addLogicalMin(0); report_map.addLogicalMax(1); report_map.addReportSize(1); report_map.addReportCount(1); report_map.addInput(0x02); // Data, Var, Abs report_map.addReportSize(7); report_map.addReportCount(1); report_map.addInput(0x03); // Const, Var, Abs (padding) report_map.addUsage(0x30); // X (LED Output) report_map.addLogicalMin(0); report_map.addLogicalMax(1); report_map.addReportSize(1); report_map.addReportCount(1); report_map.addOutput(0x02); // Data, Var, Abs report_map.addReportSize(7); report_map.addReportCount(1); report_map.addOutput(0x03); // Const, Var, Abs (padding) report_map.addEndCollection(); } void registerCharacteristics() { // 注册自定义输出特征值 GattCharacteristic* chars[] { led_control_char }; // ... 初始化 led_control_char 参数 ... // 最后调用父类注册 HIDService::registerCharacteristics(chars, sizeof(chars)/sizeof(chars[0])); } void setLED(uint8_t state) { // 实际控制硬件 LED } };4.2 两种实例化方式对比方式适用场景代码复杂度灵活性示例模板包装器Nano33BleHIDT服务构造函数单一仅BLE无额外初始化逻辑★☆☆☆☆极简★★☆☆☆固定生命周期Nano33BleHIDHIDControlPanelService panel;继承MbedBleHID需要自定义构造函数、多服务组合、复杂初始化或析构逻辑★★★★☆中等★★★★★完全可控class MyHID : public MbedBleHID { ... }; MyHID my_device;MbedBleHID的CreateHIDService(BLE)纯虚函数是核心钩子允许返回任意std::shared_ptrHIDService这使得在一个设备上同时运行鼠标、键盘和自定义服务成为可能。5. 关键 API 与配置详解5.1 核心类与函数接口类/函数参数/返回值作用注意事项Nano33BleHIDT::initialize()void初始化 BLE、注册所有服务DIS, BAS, HID、设置广播数据必须在setup()中调用且早于MbedBleHID_RunEventThread()HIDService::SendReport()void将当前report_buffer内容通过notify()发送给主机主机必须已订阅该特征值否则静默失败HIDKeyboardService::pressKey(char)void根据当前布局查找键码并填入报告缓冲区不会自动发送需后续调用SendReport()HIDMouseService::motion(int8_t x, int8_t y)void设置 X/Y 轴位移值范围 -127~127超出范围可能导致主机丢弃报告MbedBleHID_RunEventThread()void创建并启动独立的 BLE 事件处理线程若未调用所有 BLE 回调将永不触发5.2 编译时配置宏宏定义默认值作用修改方式DEMO_ENABLE_RANDOM_INPUT1启用ble_mouse示例中的随机运动演示在platformio.ini中添加build_flags -DDEMO_ENABLE_RANDOM_INPUT0HID_KEYBOARD_LAYOUTLAYOUT_US_INTERNATIONAL指定键盘布局在src/services/keylayouts.h中取消注释对应行如#define LAYOUT_DEBLE_HID_DEBUG未定义启用串口调试输出连接状态、报告内容添加-DBLE_HID_DEBUG到编译选项6. 已知限制与工程规避方案6.1 Boot Protocol 未实现HOGP 规范要求支持 Boot Protocol使 HID 设备能在操作系统启动早期如 BIOS/UEFI 阶段被识别。当前库仅实现了 Report Protocol。工程规避方案对于需要 BIOS 兼容性的场景如服务器 KVM应选用原生 USB HID 方案如 Arduino Leonardo若仅需 OS 层功能此限制无影响。6.2 连接稳定性优化在高干扰环境如 2.4GHz Wi-Fi 密集区域BLE 连接可能不稳定。实测优化方案在setup()中调用ble.gap().setScanParameters(100ms, 100ms)降低扫描功耗使用ble.gattServer().write()替代notify()进行关键控制命令如关机指令确保送达在loop()中加入连接状态检查if (!ble.gap().isConnected()) { ble.gap().connect(); }6.3 电池电量上报BatteryService默认不主动上报电量需在应用层周期性调用battery_service.updateBatteryLevel(uint8_t level)。典型实现void updateBattery() { // 读取 VBAT 引脚电压映射为 0-100% float vbat analogRead(VBAT_PIN) * 3.3f / 4095.0f; uint8_t level (uint8_t)constrain(map(vbat, 2.5f, 3.3f, 0, 100), 0, 100); battery_service.updateBatteryLevel(level); }7. 调试与故障排查7.1 常见问题诊断表现象可能原因诊断命令/方法设备在手机上可见但无法配对广播数据包超长31字节检查Nano33BleHID构造函数中设备名长度建议 ≤ 12 字符主机识别为“未知设备”DIS 服务缺失或字段为空使用 nRF Connect App 查看 GATT 浏览器确认0x180A服务存在且0x2A29(Manufacturer Name) 有值键盘按键无响应SendReport()未被调用或报告缓冲区未更新在pressKey()后添加printf(Key %d sent\n, keycode);并观察串口鼠标移动卡顿loop()执行过慢或SendReport()频率过高使用逻辑分析仪抓取BLE线确认notify()间隔是否稳定在 10-20ms7.2 使用 nRF Connect 进行深度分析nRF ConnectAndroid/iOS是调试 BLE HID 的必备工具Connect到设备后进入GATT Browser展开0x1812(HID) 服务检查0x2A4D(Report) 特征值的Client Characteristic Configuration描述符是否被主机设为0x0001Notify enabled点击0x2A4D的Notify按钮手动发送测试报告如01 00 00 00模拟左键点击观察设备端串口输出确认onDataWritten回调是否触发一套完整的 BLE HID 设备从原理图设计、PCB 布局天线匹配、固件开发到最终与 Windows/macOS 的无缝协同每一个环节都考验着嵌入式工程师的系统性思维。Mbed BLE HID 库的价值正在于它将协议栈中最晦涩的那部分——GATT 服务的组织、报告描述符的编译、以及与操作系统 HID 子系统的握手——封装成几行清晰的 C 代码。当你第一次看到 Nano 33 BLE 在没有 USB 线缆的情况下让光标在屏幕上自如移动或是敲击键盘在编辑器中留下字符那一刻所体会到的不仅是技术的胜利更是对“人机交互”这一古老命题在无线时代的一次优雅重述。

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/2436007.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

SpringBoot-17-MyBatis动态SQL标签之常用标签

文章目录 1 代码1.1 实体User.java1.2 接口UserMapper.java1.3 映射UserMapper.xml1.3.1 标签if1.3.2 标签if和where1.3.3 标签choose和when和otherwise1.4 UserController.java2 常用动态SQL标签2.1 标签set2.1.1 UserMapper.java2.1.2 UserMapper.xml2.1.3 UserController.ja…

wordpress后台更新后 前端没变化的解决方法

使用siteground主机的wordpress网站,会出现更新了网站内容和修改了php模板文件、js文件、css文件、图片文件后,网站没有变化的情况。 不熟悉siteground主机的新手,遇到这个问题,就很抓狂,明明是哪都没操作错误&#x…

网络编程(Modbus进阶)

思维导图 Modbus RTU(先学一点理论) 概念 Modbus RTU 是工业自动化领域 最广泛应用的串行通信协议,由 Modicon 公司(现施耐德电气)于 1979 年推出。它以 高效率、强健性、易实现的特点成为工业控制系统的通信标准。 包…

UE5 学习系列(二)用户操作界面及介绍

这篇博客是 UE5 学习系列博客的第二篇,在第一篇的基础上展开这篇内容。博客参考的 B 站视频资料和第一篇的链接如下: 【Note】:如果你已经完成安装等操作,可以只执行第一篇博客中 2. 新建一个空白游戏项目 章节操作,重…

IDEA运行Tomcat出现乱码问题解决汇总

最近正值期末周,有很多同学在写期末Java web作业时,运行tomcat出现乱码问题,经过多次解决与研究,我做了如下整理: 原因: IDEA本身编码与tomcat的编码与Windows编码不同导致,Windows 系统控制台…

利用最小二乘法找圆心和半径

#include <iostream> #include <vector> #include <cmath> #include <Eigen/Dense> // 需安装Eigen库用于矩阵运算 // 定义点结构 struct Point { double x, y; Point(double x_, double y_) : x(x_), y(y_) {} }; // 最小二乘法求圆心和半径 …

使用docker在3台服务器上搭建基于redis 6.x的一主两从三台均是哨兵模式

一、环境及版本说明 如果服务器已经安装了docker,则忽略此步骤,如果没有安装,则可以按照一下方式安装: 1. 在线安装(有互联网环境): 请看我这篇文章 传送阵>> 点我查看 2. 离线安装(内网环境):请看我这篇文章 传送阵>> 点我查看 说明&#xff1a;假设每台服务器已…

XML Group端口详解

在XML数据映射过程中&#xff0c;经常需要对数据进行分组聚合操作。例如&#xff0c;当处理包含多个物料明细的XML文件时&#xff0c;可能需要将相同物料号的明细归为一组&#xff0c;或对相同物料号的数量进行求和计算。传统实现方式通常需要编写脚本代码&#xff0c;增加了开…

LBE-LEX系列工业语音播放器|预警播报器|喇叭蜂鸣器的上位机配置操作说明

LBE-LEX系列工业语音播放器|预警播报器|喇叭蜂鸣器专为工业环境精心打造&#xff0c;完美适配AGV和无人叉车。同时&#xff0c;集成以太网与语音合成技术&#xff0c;为各类高级系统&#xff08;如MES、调度系统、库位管理、立库等&#xff09;提供高效便捷的语音交互体验。 L…

(LeetCode 每日一题) 3442. 奇偶频次间的最大差值 I (哈希、字符串)

题目&#xff1a;3442. 奇偶频次间的最大差值 I 思路 &#xff1a;哈希&#xff0c;时间复杂度0(n)。 用哈希表来记录每个字符串中字符的分布情况&#xff0c;哈希表这里用数组即可实现。 C版本&#xff1a; class Solution { public:int maxDifference(string s) {int a[26]…

【大模型RAG】拍照搜题技术架构速览:三层管道、两级检索、兜底大模型

摘要 拍照搜题系统采用“三层管道&#xff08;多模态 OCR → 语义检索 → 答案渲染&#xff09;、两级检索&#xff08;倒排 BM25 向量 HNSW&#xff09;并以大语言模型兜底”的整体框架&#xff1a; 多模态 OCR 层 将题目图片经过超分、去噪、倾斜校正后&#xff0c;分别用…

【Axure高保真原型】引导弹窗

今天和大家中分享引导弹窗的原型模板&#xff0c;载入页面后&#xff0c;会显示引导弹窗&#xff0c;适用于引导用户使用页面&#xff0c;点击完成后&#xff0c;会显示下一个引导弹窗&#xff0c;直至最后一个引导弹窗完成后进入首页。具体效果可以点击下方视频观看或打开下方…

接口测试中缓存处理策略

在接口测试中&#xff0c;缓存处理策略是一个关键环节&#xff0c;直接影响测试结果的准确性和可靠性。合理的缓存处理策略能够确保测试环境的一致性&#xff0c;避免因缓存数据导致的测试偏差。以下是接口测试中常见的缓存处理策略及其详细说明&#xff1a; 一、缓存处理的核…

龙虎榜——20250610

上证指数放量收阴线&#xff0c;个股多数下跌&#xff0c;盘中受消息影响大幅波动。 深证指数放量收阴线形成顶分型&#xff0c;指数短线有调整的需求&#xff0c;大概需要一两天。 2025年6月10日龙虎榜行业方向分析 1. 金融科技 代表标的&#xff1a;御银股份、雄帝科技 驱动…

观成科技:隐蔽隧道工具Ligolo-ng加密流量分析

1.工具介绍 Ligolo-ng是一款由go编写的高效隧道工具&#xff0c;该工具基于TUN接口实现其功能&#xff0c;利用反向TCP/TLS连接建立一条隐蔽的通信信道&#xff0c;支持使用Let’s Encrypt自动生成证书。Ligolo-ng的通信隐蔽性体现在其支持多种连接方式&#xff0c;适应复杂网…

铭豹扩展坞 USB转网口 突然无法识别解决方法

当 USB 转网口扩展坞在一台笔记本上无法识别,但在其他电脑上正常工作时,问题通常出在笔记本自身或其与扩展坞的兼容性上。以下是系统化的定位思路和排查步骤,帮助你快速找到故障原因: 背景: 一个M-pard(铭豹)扩展坞的网卡突然无法识别了,扩展出来的三个USB接口正常。…

未来机器人的大脑:如何用神经网络模拟器实现更智能的决策?

编辑&#xff1a;陈萍萍的公主一点人工一点智能 未来机器人的大脑&#xff1a;如何用神经网络模拟器实现更智能的决策&#xff1f;RWM通过双自回归机制有效解决了复合误差、部分可观测性和随机动力学等关键挑战&#xff0c;在不依赖领域特定归纳偏见的条件下实现了卓越的预测准…

Linux应用开发之网络套接字编程(实例篇)

服务端与客户端单连接 服务端代码 #include <sys/socket.h> #include <sys/types.h> #include <netinet/in.h> #include <stdio.h> #include <stdlib.h> #include <string.h> #include <arpa/inet.h> #include <pthread.h> …

华为云AI开发平台ModelArts

华为云ModelArts&#xff1a;重塑AI开发流程的“智能引擎”与“创新加速器”&#xff01; 在人工智能浪潮席卷全球的2025年&#xff0c;企业拥抱AI的意愿空前高涨&#xff0c;但技术门槛高、流程复杂、资源投入巨大的现实&#xff0c;却让许多创新构想止步于实验室。数据科学家…

深度学习在微纳光子学中的应用

深度学习在微纳光子学中的主要应用方向 深度学习与微纳光子学的结合主要集中在以下几个方向&#xff1a; 逆向设计 通过神经网络快速预测微纳结构的光学响应&#xff0c;替代传统耗时的数值模拟方法。例如设计超表面、光子晶体等结构。 特征提取与优化 从复杂的光学数据中自…