【从零实现JsonRpc框架#2】Muduo库介绍
1.基本概念
Muduo
由陈硕大佬开发,是一个基于非阻塞IO和事件驱动的C++高并发TCP网络编程库。它是一款基于主从Reactor模型的网络库,其使用的线程模型是 one loop per thread。
1.1 主从 Reactor 模型
- 主 Reactor(
MainReactor
,通常由EventLoop
实现):- 负责监听新连接(
accept
事件),通过Acceptor
类实现。 - 使用
epoll
/poll
等多路复用机制监控监听套接字。
- 负责监听新连接(
- 从 Reactor(
SubReactor
,多个EventLoop
线程):- 每个
EventLoop
管理一组已建立的 TCP 连接(TcpConnection
)。 - 处理连接的读写事件、定时任务和用户回调。
- 每个
1.2 One Loop Per Thread
- 线程绑定:每个
EventLoop
对象严格绑定到一个线程(通过EventLoop::loop()
在所属线程运行)。 - 资源隔离:TCP 连接的生命周期由所属
EventLoop
管理,避免跨线程竞争。 - 性能优化:通过线程局部存储(
ThreadLocal
)实现高效的事件循环访问。
2.常见接口
2.1TcpServer 类基础介绍
typedef std::shared_ptr<TcpConnection> TcpConnectionPtr;
typedef std::function<void (const TcpConnectionPtr&)> ConnectionCallback;
typedef std::function<void (const TcpConnectionPtr&, Buffer*, Timestamp)> MessageCallback;class InetAddress : public muduo::copyable
{
public:InetAddress(StringArg ip, uint16_t port, bool ipv6 = false);
};class TcpServer : noncopyable
{
public:enum Option{kNoReusePort,kReusePort,};TcpServer(EventLoop* loop, const InetAddress& listenAddr, const string& nameArg, Option option = kNoReusePort);void setThreadNum(int numThreads);void start();// 当⼀个新连接建⽴成功的时候被调用 void setConnectionCallback(const ConnectionCallback& cb){ connectionCallback_ = cb; }// 消息的业务处理回调函数---这是收到新连接消息的时候被调用的函数 void setMessageCallback(const MessageCallback& cb){ messageCallback_ = cb; }
};
-
职责:服务端入口,管理监听套接字和连接池。
-
关键流程:
- 构造时绑定
EventLoop
(主 Reactor)。 start()
启动监听,注册Acceptor
到主 Reactor。- 新连接到达时,通过轮询算法分配从 Reactor 管理。
- 构造时绑定
TcpServer(EventLoop* loop, const InetAddress& listenAddr, const string& nameArg)
:构造函数,loop
是事件循环对象,listenAddr
是监听地址,nameArg
是服务器名称。void setThreadNum(int numThreads)
:设置服务器的工作线程数。默认为 1,即单线程模式。void start()
:启动服务器,开始监听端口。void setConnectionCallback(const ConnectionCallback& cb)
:设置连接回调函数,当有新连接或连接断开时调用。void setMessageCallback(const MessageCallback& cb)
:设置消息回调函数,当有数据到达时调用。void setWriteCompleteCallback(const WriteCompleteCallback& cb)
:设置写完成回调函数,当所有数据写入完成后调用。
void setConnectionCallback(ConnectionCallback cb); // 连接建立/关闭回调
void setMessageCallback(MessageCallback cb); // 消息到达回调
示例代码:
#include <muduo/net/TcpServer.h>
#include <muduo/net/EventLoop.h>
#include <muduo/net/InetAddress.h>
#include <iostream>void onConnection(const muduo::net::TcpConnectionPtr& conn) {if (conn->connected()) {std::cout << "New connection: " << conn->name() << std::endl;} else {std::cout << "Connection closed: " << conn->name() << std::endl;}
}void onMessage(const muduo::net::TcpConnectionPtr& conn, muduo::net::Buffer* buf, muduo::Timestamp receiveTime) {std::string msg(buf->retrieveAllAsString());std::cout << "Received message: " << msg << std::endl;conn->send(msg); // 回显消息
}int main() {muduo::net::EventLoop loop;muduo::net::InetAddress listenAddr(8080);muduo::net::TcpServer server(&loop, listenAddr, "EchoServer");server.setConnectionCallback(onConnection);server.setMessageCallback(onMessage);server.setThreadNum(4); // 使用 4 个工作线程server.start();loop.loop();return 0;
}
2.2EventLoop 类基础介绍
EventLoop
是 Muduo 库的核心类之一,负责事件循环(event loop)。每个线程只能有一个 EventLoop
实例,它负责监听和分发事件(如 I/O 事件、定时器事件等)。
常用接口:
void loop()
:启动事件循环,进入事件监听状态。void quit()
:退出事件循环。void runInLoop(const Functor& cb)
:在当前EventLoop
线程中执行回调函数cb
。如果调用者不在该线程中,则将回调函数加入队列,稍后执行。void queueInLoop(const Functor& cb)
:将回调函数cb
加入队列,稍后在EventLoop
线程中执行。TimerId runAt(const Timestamp& time, const TimerCallback& cb)
:在指定的时间点time
执行回调函数cb
。TimerId runAfter(double delay, const TimerCallback& cb)
:在指定的延迟时间delay
后执行回调函数cb
。TimerId runEvery(double interval, const TimerCallback& cb)
:每隔interval
秒执行一次回调函数cb
。
成员:
std::unique_ptr<Poller> poller_; // 底层 IO 多路复用(epoll/poll)
std::vector<Functor> pendingFunctors_; // 跨线程任务队列
核心方法
void loop(); // 启动事件循环(必须在本线程调用)
void quit(); // 停止循环
void runInLoop(Functor cb); // 跨线程安全的任务提交
TimerId runAfter(double delay, TimerCallback cb); // 定时器
代码示例:
#include <muduo/net/EventLoop.h>
#include <iostream>void print() {std::cout << "Hello, EventLoop!" << std::endl;
}int main() {muduo::net::EventLoop loop;loop.runAfter(1.0, print); // 1秒后执行 print 函数loop.loop(); // 启动事件循环return 0;
}
2.3TcpConnection 基础介绍
TcpConnection
表示一个 TCP 连接。它是 TcpServer
的内部类,用于管理客户端与服务器之间的连接。每个连接都有一个唯一的 TcpConnection
对象。
void send(const void* data, int len)
:发送数据到客户端。void send(const StringPiece& message)
:发送字符串数据到客户端。void shutdown()
:关闭连接(半关闭,停止发送数据,但仍然可以接收数据)。void forceClose()
:强制关闭连接。bool connected() const
:判断连接是否处于连接状态。std::string name() const
:返回连接的名称(唯一标识符)。EventLoop* getLoop() const
:返回该连接所属的EventLoop
。
特性:
- 继承
std::enable_shared_from_this
,依赖智能指针管理生命周期。 - 通过
Channel
类注册到所属EventLoop
的Poller
。
void send(const void* data, size_t len); // 线程安全的发送接口
void shutdown(); // 半关闭连接(写端)
bool connected(); // 判断当前连接是否正常
示例代码:
void onMessage(const muduo::net::TcpConnectionPtr& conn, muduo::net::Buffer* buf, muduo::Timestamp receiveTime) {std::string msg(buf->retrieveAllAsString());std::cout << "Received message: " << msg << std::endl;if (msg == "quit\n") {conn->shutdown(); // 如果收到 "quit",关闭连接} else {conn->send(msg); // 回显消息}
}
2.4TcpClient 类基础介绍
TcpClient
用于创建 TCP 客户端。它可以连接到远程服务器并与之通信。
常用接口
TcpClient(EventLoop* loop, const InetAddress& serverAddr, const string& nameArg)
:构造函数,loop
是事件循环对象,serverAddr
是服务器地址,nameArg
是客户端名称。void connect()
:发起连接请求。void disconnect()
:断开连接。void setConnectionCallback(const ConnectionCallback& cb)
:设置连接回调函数。void setMessageCallback(const MessageCallback& cb)
:设置消息回调函数。
同步控制:
- 使用
CountDownLatch
等待连接建立完成后再发送数据:
CountDownLatch latch(1);
client.setConnectionCallback([&](const TcpConnectionPtr& conn) {if (conn->connected()) latch.countDown();
});
client.connect();
latch.wait(); // 等待连接成功
示例代码:
#include <muduo/net/TcpClient.h>
#include <muduo/net/EventLoop.h>
#include <muduo/net/InetAddress.h>
#include <iostream>void onConnection(const muduo::net::TcpConnectionPtr& conn) {if (conn->connected()) {std::cout << "Connected to server." << std::endl;conn->send("Hello, server!\n");} else {std::cout << "Disconnected from server." << std::endl;}
}void onMessage(const muduo::net::TcpConnectionPtr& conn, muduo::net::Buffer* buf, muduo::Timestamp receiveTime) {std::string msg(buf->retrieveAllAsString());std::cout << "Received from server: " << msg << std::endl;
}int main() {muduo::net::EventLoop loop;muduo::net::InetAddress serverAddr("127.0.0.1", 8080);muduo::net::TcpClient client(&loop, serverAddr, "EchoClient");client.setConnectionCallback(onConnection);client.setMessageCallback(onMessage);client.connect();loop.loop();return 0;
}
2.5.Buffer 类基础介绍
Buffer
是 Muduo 中用于处理网络数据缓冲区的类。它实现了动态缓冲区的功能,支持高效的读写操作。
常用接口
void append(const char* data, size_t len)
:向缓冲区追加数据。size_t readableBytes() const
:返回可读字节数。size_t writableBytes() const
:返回可写字节数。const char* peek() const
:返回缓冲区中可读数据的起始位置。void retrieve(size_t len)
:从缓冲区中移除已读取的数据。std::string retrieveAllAsString()
:将缓冲区中的所有数据取出并转换为字符串。void prepend(const void* data, size_t len)
:在缓冲区前面插入数据。
示例代码:
void onMessage(const muduo::net::TcpConnectionPtr& conn, muduo::net::Buffer* buf, muduo::Timestamp receiveTime) {while (buf->readableBytes() >= sizeof(int)) {const char* data = buf->peek();int be32 = *reinterpret_cast<const int*>(data);int host32 = muduo::net::sockets::networkToHost32(be32); // 转换为本地字节序buf->retrieve(sizeof(int));std::cout << "Received integer: " << host32 << std::endl;}
}
3.总结
EventLoop
:负责事件循环,监听 I/O 事件和定时器事件。TcpServer
:用于创建 TCP 服务器,监听客户端连接。TcpConnection
:表示一个 TCP 连接,负责管理客户端与服务器之间的通信。TcpClient
:用于创建 TCP 客户端,连接到远程服务器。Buffer
:用于处理网络数据缓冲区,支持高效的读写操作。
这些类是 Muduo 库的核心组件,通过它们可以轻松构建高性能的 TCP 网络应用
相关文章:
【从零实现JsonRpc框架#2】Muduo库介绍
1.基本概念 Muduo 由陈硕大佬开发,是一个基于非阻塞IO和事件驱动的C高并发TCP网络编程库。它是一款基于主从Reactor模型的网络库,其使用的线程模型是 one loop per thread。 1.1 主从 Reactor 模型 主 Reactor(MainReactor,通常…...
如何创建伪服务器,伪接口
创建伪接口一般是用于模拟真实接口的行为,以便在开发和测试过程中进行使用,以下是一些常见的创建伪接口的方法: 使用 Web 框架搭建: Python 和 Flask:Flask 是一个轻量级的 Python Web 框架。示例代码如下:…...
NX949NX952美光科技闪存NX961NX964
NX949NX952美光科技闪存NX961NX964 在半导体存储领域,美光科技始终扮演着技术引领者的角色。其NX系列闪存产品线凭借卓越的性能与创新设计,成为数据中心、人工智能、高端消费电子等场景的核心组件。本文将围绕NX949、NX952、NX961及NX964四款代表性产品…...
vue配置代理解决前端跨域的问题
文章目录 一、概述二、报错现象三、通过配置代理来解决修改request.js中的baseURL为/api在vite.config.js中增加代理配置 四、参考资料 一、概述 跨域是指由于浏览器的同源策略限制,向不同源(不同协议、不同域名、不同端口)发送ajax请求会失败 二、报错现象 三、…...
深入解析Vue3中ref与reactive的区别及源码实现
深入解析Vue3中ref与reactive的区别及源码实现 前言 Vue3带来了全新的响应式系统,其中ref和reactive是最常用的两个API。本文将从基础使用、核心区别到源码实现,由浅入深地分析这两个API。 一、基础使用 1. ref import { ref } from vueconst count…...
Java Bean容器详解:核心功能与最佳使用实践
在Java企业级开发中,Bean容器是框架的核心组件之一,它通过管理对象(Bean)的生命周期、依赖关系等,显著提升了代码的可维护性和扩展性。主流的框架如Spring、Jakarta EE(原Java EE)均提供了成熟的…...
Xilinx Kintex-7 XC7K325T-2FFG676I 赛灵思 FPGA
XC7K325T-2FFG676I 属于 Kintex-7 FPGA ,低功耗与合理成本的应用市场,可提供比前代产品两倍的性价比提升和卓越的系统集成能力。该器件于 28 nm 工艺节点制造,速度等级为 -2,适合对时序要求严格但预算有限的系统设计。 产品架构与…...
AI实战笔记(1)AI 的 6 大核心方向 + 学习阶段路径
一、机器学习(ML) 目标:用数据“训练”模型,完成分类、回归、聚类等任务。 学习阶段: (1)基础数学:线性代数、概率统计、微积分(适度) (2…...
Ceph集群故障处理 - PG不一致修复
Ceph集群故障处理 - PG不一致修复 目录故障现象故障分析故障定位修复过程磁盘状态检查OSD存储结构检查修复分析故障总结问题原因修复方法后续建议经验教训最佳实践 参考资料 # ceph -v ceph version 14.2.22目录 故障现象故障分析故障定位修复过程磁盘状态检查OSD存储结构检查…...
【前端】每日一道面试题3:如何实现一个基于CSS Grid的12列自适应布局?
要实现一个基于CSS Grid的12列自适应布局,关键在于利用网格系统的灵活性和响应式设计能力。以下是具体实现步骤及核心代码示例: 一、基础网格容器定义 创建网格容器 使用display: grid将父元素定义为网格容器: .container {display: grid;gr…...
leetcode 349. Intersection of Two Arrays
题目描述 题目限制0 < nums1[i], nums2[i] < 1000,所以可以开辟一个1001个元素的数组来做哈希表。 class Solution { public:vector<int> intersection(vector<int>& nums1, vector<int>& nums2) {vector<int> table(1001,0…...
机器学习 day01
文章目录 前言一、机器学习的基本概念二、数据集的加载1.玩具数据集2.联网数据集3.本地数据集 三、数据集的划分四、特征提取1.稀疏矩阵与稠密矩阵2.字典列表特征提取3.文本特征提取 前言 目前我开始学习机器学习部分的相关知识,通过今天的学习,我掌握了…...
C++STL——priority_queue
优先队列 前言优先队列仿函数头文件 前言 本篇主要讲解优先队列及其底层实现。 优先队列 优先队列的本质就是个堆,其与queue一样,都是容器适配器,不过优先队列是默认为vector实现的。priority_queue的接口优先队列默认为大根堆。 仿函数 …...
DS18B20温度传感器
1.基本信息 测温范围为一55~ 125℃;3.3/5V的供电电压;-10~85内精度较高; 典型的温度转换时间为 750ms(12 位分辨率); 输出最小分辨率:0.0625; 采用单总线数据格式&am…...
《Python星球日记》 第50天:深度学习概述与环境搭建
名人说:路漫漫其修远兮,吾将上下而求索。—— 屈原《离骚》 创作者:Code_流苏(CSDN)(一个喜欢古诗词和编程的Coder😊) 目录 一、什么是深度学习?它与传统机器学习的区别1. 深度学习的定义2. 深…...
BUUCTF——Cookie is so stable
BUUCTF——Cookie is so stable 进入靶场 页面有点熟悉 跟之前做过的靶场有点像 先简单看一看靶场信息 有几个功能点 flag.php 随便输了个admin 根据题目提示 应该与cookie有关 抓包看看 构造payload Cookie: PHPSESSIDef0623af2c1a6d2012d57f3529427d52; user{{7*7}}有…...
Java 基础面试题
🧑 博主简介:CSDN博客专家,历代文学网(PC端可以访问:https://literature.sinhy.com/#/literature?__c1000,移动端可微信小程序搜索“历代文学”)总架构师,15年工作经验,…...
bcm5482 phy 场景总结
1,BCM5482是一款双端口10/100/1000BASE-T以太网PHY芯片,支持多种速率和双工模式。其配置主要通过MDIO(Management Data Input/Output)接口进行,MDIO接口用于访问PHY芯片内部的寄存器,从而配置网络速率、双工模式以及其他相关参数。 a,具体以下面两种场景举例 2. 寄存器和…...
小程序多线程实战
在小程序开发中,由于微信小程序的运行环境限制,原生并不支持传统意义上的多线程编程,但可以通过以下两种核心方案实现类似多线程的并发处理效果,尤其在处理复杂计算、避免主线程阻塞时非常关键: 一、官方方案ÿ…...
PPT图表怎么制作?说5款自己使用过的PPT图表制作工具
PPT图表怎么制作?准备一份吸引人的PPT演示文稿时,图表往往能起到画龙点睛的作用。但是,对于很多人来说,制作既美观又专业的图表却不是一件容易的事情。今天,我们就来聊聊如何利用一些优秀的工具制作PPT图表。 1、亿图图…...
渠道销售简历模板范文
模板信息 简历范文名称:渠道销售简历模板范文,所属行业:其他 | 职位,模板编号:KRZ3J3 专业的个人简历模板,逻辑清晰,排版简洁美观,让你的个人简历显得更专业,找到好工作…...
数据库实验10
设计性实验 1.实验要求 1.编写函数FsumXXX,1~n(参数)求和; GO CREATE FUNCTION Fsum065 (n INT) RETURNS INT AS BEGIN DECLARE sum INT 0 WHILE n > 0 BEGIN SET sum sum n SET n n - 1 END RETURN sum END …...
C#异步Task,await,async和Unity同步协程
标题 TaskawaitasyncUnity协程 Task Task是声明异步任务的必要关键字,也可以使用Task<>泛型来定义Task的返回值。 await await是用于等待一个Task结束,否则让出该线程控制权,让步给其他线程,直到该Task结束才往下运行。 …...
【ML-Agents】ML-Agents示例项目导入unity报错解决
最近在跑ML-Agents的示例代码,无奈往unity中导入项目后,就出现报错。本文简要描述了各个报错的解决方法。 文章目录 一、error CS0234: The type or namespace name InputSystem does not exist in the namespace UnityEngine (are you missing an assem…...
【Web前端开发】HTML基础
Web前端开发是用来直接给用户呈现一个一个的网页,主要包含实现用户的结构(HTML)、样式(CSS)、交互(JavaScript)。然而一个软件通常是由后端和前端完成的。可以查阅文档:HTML 教程 (w…...
spark-哈希join介绍
目录 1. Shuffle Join 和 Hash Join 的复杂度1.1 Shuffle Join1.2 Hash Join 2. 哈希算法的原理2.1 什么是哈希算法?2.2 哈希算法的工作原理2.3 常见哈希函数 3. 哈希算法的弊端3.1 哈希碰撞3.2 哈希分布不均匀3.3 哈希值不可逆 4. 哈希碰撞的处理方法4.1 链地址法4…...
计算机网络与多线程同步机制详解
一、IP地址与子网划分 在互联网世界中,IP地址就像是每个设备的"门牌号",它使得数据包能够准确送达目的地。IP地址的划分与管理就像城市的规划,通过合理的子网划分,能够高效地管理网络资源。 子网掩码的工作原理 子网…...
栈溢出攻击最基本原理
函数在调用的过程中,函数在调用之前呢,会将调用完这个函数之后的下一条命令的地址保存到LR中。 void func() {int a[4];a[6] 100; } 这个函数在用gcc编译的时候是不会报错的,所以我们可以在尝试之后,修改LR的值,让代…...
ChemDraw、InDraw、KingDraw有什么差别?
在化学相关的科研与教学领域,一款好用的结构式编辑器至关重要,ChemDraw因此闻名;但近年来,ChemDraw代理商频繁发送律师函,给学校和企业带来诸多困扰,促使大家纷纷寻找替代软件。InDraw和KingDraw这两款软件…...
NVMe控制器IP设计之接口模块
这是NVMe控制器IP设计系列博客之一,其他的见本博客或csdn搜用户名:tiantianuser。相关视频见B站用户名:专注与守望。 接口转换模块负责完成AXI4接口与控制器内部的自定义接口之间的转换工作。接口转换模块的框图如图1所示。 图1 接口转换示…...
从0开始学linux韦东山教程第三章问题小结(2)
本人从0开始学习linux,使用的是韦东山的教程,在跟着课程学习的情况下的所遇到的问题的总结,理论虽枯燥但是是基础。 摘要关键词:PC远程访问ubuntu配置,ubuntu配置uboot环境,串口控制开发板 本文详细介绍以下问题&…...
JS正则表达式介绍(JavaScript正则表达式)
文章目录 JavaScript正则表达式完全指南正则表达式基础元字符与特殊字符基本元字符. - 点号\d - 数字\D - 非数字\w - 单词字符\W - 非单词字符\s - 空白字符\S - 非空白字符 正则表达式标志常用标志详解g - 全局匹配i - 忽略大小写m - 多行匹配s - 点号匹配所有字符u - Unicod…...
(51单片机)LCD显示红外遥控相关数字(Delay延时函数)(LCD1602教程)(Int0和Timer0外部中断教程)(IR红外遥控模块教程)
前言: 本次Timer0模块改装了一下,注意!!!今天只是简单的实现一下,明天用次功能显示遥控密码锁 演示视频: 在审核 源代码: 如上图将9个文放在Keli5 中即可,然后烧录在…...
关于单片机的基础知识(一)
成长路上不孤单😊😊😊😊😊😊 【14后😊///计算机爱好者😊///持续分享所学😊///如有需要欢迎收藏转发///😊】 今日分享关于单片机基础知识的相关内容…...
操作系统学习笔记第2章 (竟成)
第 2 章 进程管理 【考纲内容】 1.进程与线程: (1) 进程 / 线程的基本概念; (2) 进程 / 线程的状态与转换; (3) 线程的实现:内核支持的线程;线程库支持的线程; (4) 进程与线程的组织与控制; (5)…...
《从零开始:构建你的第一个区块链应用》
一、引言 区块链技术,这个曾经只在金融领域被广泛讨论的技术,如今已经渗透到各个行业。从供应链管理到智能合约,区块链的应用场景越来越丰富。对于开发者来说,理解区块链的基本原理并构建一个简单的区块链应用,是进入这…...
[思维模式-24]:《本质思考力》-5- 马克思主义毛泽东思想揭示了了人类社会运作的普遍规律有哪些?
目录 一、马克思主义毛泽东思想揭示了了人类社会运作的普遍规律有哪些? 1、生产力与生产关系的辩证运动规律 2、阶级斗争与社会革命规律 3、社会形态演变规律 4、人民群众是历史创造者的规律 5、社会基本矛盾运动规律 6、认识与实践的辩证关系规律 二、马克…...
CentOS7.9部署FunASR实时语音识别接口 | 部署商用级别实时语音识别接口FunASR
0. 环境说明 本次在云服务器中部署一套实时语音识别接口,基于阿里开源的FunASR。 云服务器使用莱卡云,4核心4GB内存50GB存储空间,带宽10Mbps。 操作系统使用CentOS7.9 视频演示可以看 云服务器中部署实时语音识别接口 | FunASR在云服务器…...
炫酷粒子系统动画实战:Matplotlib实现银河漩涡效果
炫酷粒子系统动画实战:Matplotlib实现银河漩涡效果 效果演示:银河粒子漩涡核心代码分析1. 粒子系统初始化2. 动画更新函数3. 渲染优化技巧 完整实现代码Matplotlib的动画模块介绍核心类对比核心功能分点注意事项 效果演示:银河粒子漩涡 动…...
MAD-TD: MODEL-AUGMENTED DATA STABILIZES HIGH UPDATE RATIO RL
ICLR 2025 spotlight paper 构建能够在少量样本下学习出优良策略的深度强化学习(RL)智能体一直是一个极具挑战性的任务。为了提高样本效率,近期的研究尝试在每获取一个新样本后执行大量的梯度更新。尽管这种高更新-数据比(UTD&am…...
机器学习第四讲:无监督学习 → 给无标签积木自由组合,发现隐藏规律
机器学习第四讲:无监督学习 → 给无标签积木自由组合,发现隐藏规律 资料取自《零基础学机器学习》。 查看总目录:学习大纲 关于DeepSeek本地部署指南可以看下我之前写的文章:DeepSeek R1本地与线上满血版部署:超详细…...
Vue 两种导航方式
目录 一、声明式导航 二、编程式导航 三、两句话总结 一、声明式导航 1. 传参跳转: <router-link :to"/user?nameCHEEMS&id114514">Query传参 </router-link><router-link :to"/user?参数名1参数值1&参数名2参数值2&a…...
HTTP 的发展史:从前端视角看网络协议的演进
别再让才华被埋没,别再让github 项目蒙尘!github star 请点击 GitHub 在线专业服务直通车GitHub赋能精灵 - 艾米莉,立即加入这场席卷全球开发者的星光革命!若你有快速提升github Star github 加星数的需求,访问taimili…...
Spring 必会之微服务篇(2)
经过上一篇文章的介绍,应该对微服务有了基本的认识,以及为什么要用微服务和微服务要面临的挑战和对应的解决问题,这一期继续聊聊关于微服务的相关知识。 服务拆分 为什么拆 对于大多数的小型项目来说,一般是先采用单体架构,但是随着后面的用户规模变大,业务越来越复杂…...
21.【.NET 8 实战--孢子记账--从单体到微服务--转向微服务】--单体转微服务--身份认证服务拆分规划
从这篇文章开始我们将开始一步一步的拆分现有的单体应用孢子记账项目。按照上一篇文章中的介绍,我们首先把身份认证服务拆分出来。 一、功能分析 在当前的单体应用中,身份认证服务主要负责用户认证、授权以及角色权限管理等核心功能。 在拆分之前&…...
人工智能100问☞第19问:什么是专家系统?
目录 一、通俗解释 二、专业解析 三、权威参考 专家系统是基于知识库(存储专家经验与规则)和推理机(模拟专家逻辑判断)的人工智能程序,能在特定领域(如医疗诊断、工业控制)高效解决复杂问题。 一、通俗解释 专家系统就像个“智能版老师傅…...
AutoGen+Deepseek+chainlit的简单使用
AutoGen 的应用场景 AutoGen 作为一个强大的多智能体协作框架,可用于多种复杂任务: 自动化工作流:构建由多个智能体组成的流水线,例如数据收集、分析、报告生成复杂问题分解:将难题拆解为子任务,分配给不…...
贪心算法专题(Part1)
目录 1. 贪心算法简介 2. 柠檬水找零 3. 将数组和减半的最少操作次数 4. 递增的三元子序列 5. K次取反后最大化的数组和 6. 增减字符串匹配 7. 分发饼干 8. 整数替换 1. 贪心算法简介 2. 柠檬水找零 题目链接:860. 柠檬水找零 - 力扣(LeetCode…...
PyTorch API 4 - 分布式通信、分布式张量
文章目录 分布式通信包 - torch.distributed后端支持PyTorch 内置的后端选择哪个后端?常见环境变量选择使用的网络接口其他NCCL环境变量 基础概念初始化返回类型:boolTCP初始化共享文件系统初始化环境变量初始化方法 初始化后操作关闭处理重新初始化 组D…...
《类和对象(中)》
引言: 上次我们主要学习了类的相关知识,今天我们就来学习类和对象(中),今天也会用到之前学习过的东西,可以说是前面知识的结合,较前面会难一点(打个预防针)。 一:类的默认成员函数…...