当前位置: 首页 > article >正文

【STL】vector介绍(附部分接口模拟实现)

文章目录

  • 1.介绍
  • 2.使用
    • 2.1 vector的构造
    • 2.2 vector空间相关接口
      • 2.2.1 size()
      • 2.2.2 capacity()
      • 2.2.3 empty()
      • 2.2.4 resize()
      • 2.2.5 reserve()
    • 2.3 vector的增删查改
      • 2.3.1 push_back()
      • 2.3.2 insert()
      • 2.3.3 pop_back()
      • 2.3.4 erase()
      • 2.3.5 swap()
      • 2.3.6 operator[]
      • 注:关于查找find()
    • 2.4 其它
      • 2.4.1 at()
      • 2.4.2 front()和back()
  • 3.部分接口的模拟实现

1.介绍

​ vector容器是一种大小可变的序列容器,可以看作一个动态数组,其采用连续的存储空间来存储元素,允许动态插入和删除元素,可以自动管理内存空间,当需要的内存空间大小大于当前内存空间大小时,会自动分配一个更大的新的数组,将全部元素转移过来,其也具备可迭代性。

2.使用

​ 同样,在使用上,这里只介绍一些经常使用的接口函数。

2.1 vector的构造

1.定义

构造函数声明说明
vector()无参构造
vector(size_type n,const value_type& val = value_type())构造并用n个val初始化
vector(const vector& x)拷贝构造
vector(InputIterator first, InputIterator last)使用迭代器进行初始化构造

2.使用

#include <iostream>
#include <vector>//包含头文件using namespace std;template<typename T>
void PrintVector(vector<T>& v)
{for (auto e : v){cout << e << " ";}cout << endl;
}void test1()
{//vector的构造 <>中的类型可以修改vector<int> v1;//无参构造vector<int> v2(10, 2);//用10个2初始化构造vector<int> v3(v2);//用v2拷贝构造vector<int> v4(v2.begin() + 1, v2.end() - 1);//迭代器构造从v2的begin() + 1到end() - 1位置PrintVector(v1);PrintVector(v2);PrintVector(v3);PrintVector(v4);
}int main()
{test1();return 0;
}

结果如下:

在这里插入图片描述

2.2 vector空间相关接口

2.2.1 size()

1.声明及作用:

声明作用
size_type size() const;获取有效数据个数

2.使用:

void test2()
{vector<int> nums({ 1,2,3,4,5,6 });size_t nums_len = nums.size();cout << nums_len << endl;//6
}int main()
{test2();return 0;
}

2.2.2 capacity()

1.声明及作用:

声明作用
size_type capacity() const;获取空间容量大小

2.使用:

void test3()
{vector<int> nums;size_t capacity = nums.capacity();//使用for (size_t i = 1; i <= 100; i++){nums.push_back(1);//尾插100个1size_t new_capacity = nums.capacity();//使用//如果空间容量大小发生变化,打印新的大小if (new_capacity != capacity){capacity = new_capacity;cout << capacity << endl;}}
}
int main()
{test3();return 0;
}输出结果为:
1
2
3
4
6
9
13
19
28
42
63
94
141

​ 这里我们通过尾插100个1顺便观察VS下vector的扩容规律:其capacity是按1.5倍增长的,注:在不同的环境下vector的增容不一定相同,比如:在Linux g++下其可能是按2倍扩容。

2.2.3 empty()

1.声明及作用:

声明作用
bool empty() const;判断该vector是否为空

2.使用:

void test4()
{vector<int> v1;if (v1.empty()){cout << "v1是空的" << endl;}else{cout << "v1是非空的" << endl;}vector<int> v2{1,2,3,4};if (v2.empty()){cout << "v2是空的" << endl;}else{cout << "v2是非空的" << endl;}
}
int main()
{test4();return 0;
}
输出:
v1是空的
v2是非空的

2.2.4 resize()

1.声明及作用:

声明作用
void resize (size_type n, value_type val = value_type());指定vector有效size大小为n,当n大于当前 vector的大小时,resize()会在vector末尾添加新元素val,不填val则为默认值。当n小于当前vector的大小时,resize()会移除vector末尾的元素,使vector的大小变为n。

2.使用:

template<typename T>
void PrintVector(vector<T>& v)
{for (auto e : v){cout << e << " ";}cout << endl;
}void test5()
{vector<int> v;v.resize(10, 1);//n=10>当前size,在末尾添加10个val = 1;PrintVector(v);//打印vv.resize(20);//n=20>当前size,在末尾添加10个val,默认为0;PrintVector(v);v.resize(5);//n=5<当前size,从末尾移除元素直至size=5PrintVector(v);
}
int main()
{test5();return 0;
}

结果如下:

在这里插入图片描述

2.2.5 reserve()

1.声明及作用:

声明作用
void reserve (size_type n);预先分配至少能容纳数量为n的内存空间,它会增加vector的capacity但不会改变有效元素的数量size

2.使用:

void test6()
{vector<int> v;cout << "before reserve'size:" << v.size() << endl;cout << "before reserve'capacity:" << v.capacity()<< endl;v.reserve(20);cout << "after reserve'size:" << v.size() << endl;//不改变sizecout << "after reserve'capacity:" << v.capacity() << endl;//增加capacity
}
int main()
{test6();return 0;
}

结果如下:

在这里插入图片描述

​ 当我们知道需要大概多少的空间大小时,我们可以通过reserve提前开辟空间以缓解vector增容的代价。

2.3 vector的增删查改

2.3.1 push_back()

1.声明及作用

声明作用
void push_back (const value_type& val);尾插val

2.使用:

template<typename T>
void PrintVector(vector<T>& v)
{for (auto e : v){cout << e << " ";}cout << endl;
}void test7()
{vector<int> v;v.push_back(1);v.push_back(2);v.push_back(3);v.push_back(4);v.push_back(5);PrintVector(v);//1 2 3 4 5
}
int main()
{test6();return 0;
}

2.3.2 insert()

1.声明及作用

声明作用
iterator insert (const_iterator position, const value_type& val);在position位置的值前插入val
iterator insert (const_iterator position, size_type n, const value_type& val);在position位置的值前插入n个val

2.使用:

template<typename T>
void PrintVector(vector<T>& v)
{for (auto e : v){cout << e << " ";}cout << endl;
}
void test8()
{vector<int> v;v.insert(v.begin(), 1);//在起始位置前插入1(相当于头插)PrintVector(v);//1v.insert(v.end(), 2);//在结束位置前插入1(相当于尾插)PrintVector(v);//1 2v.insert(v.begin() + 1, 5, 3);//在begin()+1位置前插入5个3PrintVector(v);//1 3 3 3 3 3 2
}
int main()
{test8();return 0;
}

2.3.3 pop_back()

1.声明及作用

声明作用
void pop_back();尾删

2.使用

template<typename T>
void PrintVector(vector<T>& v)
{for (auto e : v){cout << e << " ";}cout << endl;
}
void test9()
{vector<int> v;v.push_back(1);v.push_back(2);v.push_back(3);v.push_back(4);v.push_back(5);PrintVector(v);//1 2 3 4 5v.pop_back();//尾删PrintVector(v);//1 2 3 4v.pop_back();PrintVector(v);//1 2 3v.pop_back();PrintVector(v);//1 2v.pop_back();PrintVector(v);//1v.pop_back();PrintVector(v);//
}
int main()
{test9();return 0;
}

2.3.4 erase()

1.声明及作用

声明作用
iterator erase (const_iterator position);删除position位置的值
iterator erase (const_iterator first, const_iterator last);从first位置开始删到last位置前(左闭右开)

2.使用

void test10()
{vector<int> v;for (int i = 1; i <= 10; i++){v.push_back(i);}PrintVector(v);//1 2 3 4 5 6 7 8 9 10v.erase(v.begin() + 5);//删除begin()+5位置的值(6)PrintVector(v);//1 2 3 4 5 7 8 9 10v.erase(v.begin() + 1, v.end() - 1);PrintVector(v);//1 10
}
int main()
{test10();return 0;
}

2.3.5 swap()

1.声明及作用

声明作用
void swap (vector& x);交换两个vector的数据空间

2.使用

template<typename T>
void PrintVector(vector<T>& v)
{for (auto e : v){cout << e << " ";}cout << endl;
}
void test11()
{vector<int> v1(5, 1);vector<int> v2(10, 2);cout << "before swap v1:";PrintVector(v1);cout << "before swap v2:";PrintVector(v2);v1.swap(v2);//交换v1和v2cout << "after swap v1:";PrintVector(v1);cout << "after swap v2:";PrintVector(v2);
}
int main()
{test11();return 0;
}

结果如下:

在这里插入图片描述

2.3.6 operator[]

1.声明及作用

声明作用
reference operator[] (size_type n);用于非const对象,返回vector中索引为n的值,可进行读取和修改
const_reference operator[] (size_type n) const;用于const对象,返回vector中索引为n的值,只能进行读取

2.使用

void test12()
{//非const对象vector<int> v1;for (int i = 1; i <= 10; i++){v1.push_back(i);}for (int i = 0; i < 10; i++){cout << v1[i] << " ";//读取索引为i的值}cout << endl;for (int i = 0; i < 10; i++){++v1[i];//修改索引为i的值}for (int i = 0; i < 10; i++){cout << v1[i] << " ";}cout << endl;//const对象const vector<int> v2(10, 2);for (int i = 0; i < 10; i++){cout << v2[i] << " ";//读取索引为i的值}cout << endl;//for (int i = 0; i < 10; i++)//{//	++v2[i];//不允许修改//}
}
int main()
{test12();return 0;
}

结果如下:

在这里插入图片描述

注:关于查找find()

​ 在vector中没有单独添加find()的接口函数,可以使用算法板块的查找操作,这里举个例子:

void test13()
{vector<int> v;v.push_back(1);v.push_back(2);v.push_back(3);v.push_back(4);v.push_back(5);v.push_back(6);v.push_back(7);PrintVector(v);//1 2 3 4 5 6 7v.insert(find(v.begin(),v.end(),4), 5, 3);//通过find从v的begin到end区间找到4,并返回4的位置,在该位置前插入5个3PrintVector(v);//1 2 3 3 3 3 3 3 4 5 6 7
}
int main()
{test13();return 0;
}

2.4 其它

2.4.1 at()

1.作用:返回索引值位置的值,对于非const对象可以进行读取和修改,对于const对象只能读取

2.使用:

void test14()
{vector<int> v1{1,2,3,4,5};cout << v1.at(0) << endl;//1++v1.at(0);cout << v1.at(0) << endl;//2const vector<int> v2{1,2,3,4,5};cout << v2.at(2) << endl;//3//++v2.at(2);   const对象  不允许修改
}
int main()
{test14();return 0;
}

2.4.2 front()和back()

1.作用:front()返回容器中的首元素,back()返回容器中的末尾元素

2.使用:

void test15()
{vector<int> v{ 1,2,3,4,5,6 };cout << "front():" << v.front() << endl;//front():1cout << "back():" << v.back() << endl;//back():6
}int main()
{test15();return 0;
}

3.部分接口的模拟实现

​ 这里仅给出代码,不做详细介绍,有任何问题欢迎提出讨论。

#pragma once
#include <iostream>
#include <assert.h>
using namespace std;namespace myVector
{template<class T>class vector{public:// Vector的迭代器是一个原生指针typedef T* iterator;typedef const T* const_iterator;// construct and destroyvector(){}/*vector(size_t n, const T& value = T()){resize(n, value);}*//*vector(int n, const T& val = T()){resize(n, val);}*/vector(int n, const T& value = T()){assert(n >= 0);reserve(n);for (int i = 0; i < n; i++){_start[i] = value;}_finish = _start + n;}vector(size_t n, const T& value = T()){reserve(n);for (int i = 0; i < n; i++){_start[i] = value;}_finish = _start + n;}vector(const vector<T>& v){reserve(v.capacity());for (const auto& e : v){push_back(e);}}template <class InputIterator>vector(InputIterator first, InputIterator last){while (first != last){push_back(*first);++first;}}/*vector(const vector<T>& v){_start = new T[v.capacity()];memcpy(_start, v._start, v.size()* sizeof(T));_finish = _start + v.size();_endofstorage = _start + v.capacity();}*//*vector<T>& operator=(vector<T> v){swap(v);return *this;}*/vector<T>& operator=(vector<T> v){T* tmp = new T[v.size()];if (v._start){for (int i = 0; i < v.size(); i++){tmp[i] = v[i];}}_start = tmp;_finish = _start + v.size();_endOfStorage = _start + v.capacity();return *this;}~vector(){if (_start){delete[] _start;_start = nullptr;_finish = nullptr;_endOfStorage = nullptr;}}iterator begin(){return _start;}iterator end(){return _finish;}const_iterator begin() const{return _start;}const_iterator end() const{return _finish;}// capacitysize_t size() const{return _finish - _start;}size_t capacity() const{return _endOfStorage - _start;}void reserve(size_t n){if (n > capacity()){size_t old = size();T* tmp = new T[n];if (_start){for (size_t i = 0; i < old; i++){tmp[i] = _start[i];}}delete[] _start;_start = tmp;_finish = _start + old;_endOfStorage = _start + n;}}void resize(size_t n, const T& value = T()){if (n > capacity()){reserve(n);while (_finish < _start + n){*_finish = value;++_finish;}}else{_finish = _start + n;}}T& operator[](size_t pos){return _start[pos];}const T& operator[](size_t pos)const{return _start[pos];}void push_back(const T& x){if (_finish == _endOfStorage){size_t new_capacity = capacity() == 0 ? 4 : capacity() * 2;reserve(new_capacity);}*_finish = x;++_finish;}void pop_back(){assert(size() > 0);--_finish;}void swap(vector<T>& v){std::swap(_start, v._start);std::swap(_finish, v._finish);std::swap(_endOfStorage, v._endOfStorage);}iterator insert(iterator pos, const T& x){assert(pos >= _start && pos <= _finish);if (_finish == _endOfStorage){size_t len = pos - _start;size_t new_capacity = capacity() == 0 ? 4 : capacity() * 2;reserve(new_capacity);pos = _start + len;}iterator end = _finish - 1;while (end >= pos){*(end + 1) = *end;--end;}*pos = x;++_finish;return pos;}iterator erase(iterator pos){assert(pos >= _start && pos <= _finish);iterator it = pos + 1;while (it < _finish){*(it - 1) = *it;++it;}--_finish;return pos;}private:iterator _start = nullptr; //指向数据块的开始iterator _finish = nullptr; //指向有效数据的尾iterator _endOfStorage = nullptr; //指向存储容量的尾};void print_vector(const vector<int>& v){for (auto e : v){cout << e << " ";}cout << endl;}
}

相关文章:

【STL】vector介绍(附部分接口模拟实现)

文章目录 1.介绍2.使用2.1 vector的构造2.2 vector空间相关接口2.2.1 size()2.2.2 capacity()2.2.3 empty()2.2.4 resize()2.2.5 reserve() 2.3 vector的增删查改2.3.1 push_back()2.3.2 insert()2.3.3 pop_back()2.3.4 erase()2.3.5 swap()2.3.6 operator[]注&#xff1a;关于…...

一周掌握Flutter开发--8. 调试与性能优化(上)

文章目录 8. 调试与性能优化核心技能8.1 使用 Flutter DevTools 分析性能8.2 检查 Widget 重绘&#xff08;debugPaintSizeEnabled&#xff09;8.3 解决 ListView 卡顿&#xff08;ListView.builder itemExtent&#xff09; 其他性能优化技巧8.4 减少 build 方法的调用8.5 使用…...

游戏引擎学习第182天

回顾和今天的计划 昨天的进展令人惊喜&#xff0c;原本的调试系统已经被一个新的系统完全替换&#xff0c;新系统不仅能完成原有的所有功能&#xff0c;还能捕获完整的调试信息&#xff0c;包括时间戳等关键数据。这次的替换非常顺利&#xff0c;效果很好。 今天的重点是在此基…...

2025计算机毕设全流程实战指南:Java/Python+协同过滤+小程序开发避坑手册​

技术框架的选择是项目开发的关键起点&#xff0c;直接影响开发效率和最终成果质量。然而&#xff0c;许多开发者在选择技术框架时面临困难&#xff1a;现有知识储备不足以支撑复杂项目需求&#xff0c;团队经验有限&#xff0c;框架选择缺乏前瞻性常导致后期问题。尽管技术框架…...

C语言_数据结构_二叉树

【本节目标】 树的概念及结构 二叉树的概念及结构 二叉树的顺序结构及实现 二叉树的链式结构及实现 1. 树的概念及结构 1.1 树的概念 树是一种非线性的数据结构&#xff0c;它是由n&#xff08;n>0&#xff09;个有限结点组成一个具有层次关系的集合。把它叫做树是因为…...

Compare全目录文件比较内容(项目中用到过)

第一步&#xff1a;找到“会话”——“会话设置” 会话设置弹框信息 第二步&#xff1a;选择“比较”tab标签 比较内容&#xff1a;选中二进制比较 第三步&#xff1a;选中所有文件 第四步&#xff1a;右键选中“比较内容” 第五步&#xff1a;选中“基于规则的比较”...

3.26[a]paracompute homework

5555 负载不平衡指多个线程的计算量差异显著&#xff0c;导致部分线程空转或等待&#xff0c;降低并行效率。其核心矛盾在于任务划分的静态性与计算动态性不匹配&#xff0c;尤其在处理不规则数据或动态任务时尤为突出。以稀疏矩阵的向量乘法为例&#xff0c;假设其非零元素分…...

视觉大模型CLIP论文精读

论文&#xff1a;Learning Transferable Visual Models From Natural Language Supervision 代码&#xff1a;https://github.com/openai/CLIP 摘要 最先进的计算机视觉系统是针对预测一组固定的、预先确定的对象类别进行训练的。这种受限的监督形式限制了它们的通用性和可用…...

【AI】Orin NX+ubuntu22.04上移植YoloV11,并使用DeepStream测试成功

【AI】郭老二博文之:AI学习目录汇总 1、烧写系统 新到的开发板,已经烧写好Ubuntu系统,版本为22.04。 如果没有升级到Ubuntu22.04,可以在电脑Ubuntu系统中使用SDKManager来烧写Ubuntu系统,网络情况好的话,也可以直接将CUDA、cuDNN、TensorRT、Deepstream等也安装上。 2…...

HTML文档流

1. 基础定义 “文档流(Normal Flow)是指HTML元素在页面中默认的排列方式。在标准文档流中&#xff0c;块级元素会从上到下垂直排列&#xff0c;每个元素占据一整行&#xff1b;而行内元素则从左到右水平排列&#xff0c;直到空间不足才会换行。” 2. 详细解释 可以进一步展开…...

链表的创建:头插法与尾插法详解(数据结构)

C 链表的创建&#xff1a;头插法与尾插法详解 链表&#xff08;Linked List&#xff09;是一种重要的数据结构&#xff0c;适用于插入和删除操作频繁的场景。本文介绍 两种常见的链表构建方法&#xff1a; 尾插法&#xff08;Append / Tail Insertion&#xff09;&#xff1a;…...

MyBatis中mapper.xml 的sql映射规则

一、SQL 映射文件核心元素 MyBatis 映射文件的顶级元素&#xff08;按定义顺序&#xff09;&#xff1a; cache&#xff1a;命名空间的缓存配置。cache-ref&#xff1a;引用其他命名空间的缓存。resultMap&#xff1a;自定义结果集映射。sql&#xff1a;可重用的 SQL 片段。i…...

深入解析 Java 类加载机制及双亲委派模型

&#x1f50d; Java的类加载机制是确保应用程序正确运行的基础&#xff0c;特别是双亲委派模型&#xff0c;它通过父类加载器逐层加载类&#xff0c;避免冲突和重复加载。但在某些特殊场景下&#xff0c;破坏双亲委派模型会带来意想不到的效果。本文将深入解析Java类加载机制、…...

糖尿病大模型预测及临床应用研究智能管理系统技术文档

目录 1. 数据工程规范1.1 多源数据集成1.2 特征工程架构 2. 核心模型架构2.1 分层预测网络2.2 动态血糖预测模块 3. 实时决策系统3.1 术中预警协议3.2 麻醉方案优化器 4. 验证体系实现4.1 数字孪生验证平台4.2 临床验证流程 5. 系统部署方案5.1 边缘计算架构5.2 性能指标 6. 安…...

MySQL数据库精研之旅第四期:解锁库操作高阶技能

专栏&#xff1a;MySQL数据库成长记 个人主页&#xff1a;手握风云 目录 一、查看所有表 1.1. 语法 二、创建表 2.1. 语法 2.2. 示例 2.3. 表在磁盘上对应的⽂件 三、查看表结构 3.1. 语法 3.2. 示例 四、修改表 4.1. 语法 4.2. 示例 五、删除表 5.1. 语法 5.2.…...

【DevOps】DevOps and CI/CD Pipelines

DevOps 是一种将开发与运维实践相结合的模式&#xff0c;旨在缩短软件开发周期并交付高质量软件。 DevOps 是什么&#xff1f; 开发团队与运维团队之间的协作 • 持续集成与持续交付&#xff08;CI/CD&#xff09; • 流程自动化 • 基础设施即代码&#xff08;IaC&#xff09;…...

Oracle详解

Oracle 数据库是一款由 Oracle 公司开发和维护的关系数据库管理系统&#xff08;RDBMS&#xff09;。Oracle 数据库广泛应用于企业级应用中&#xff0c;尤其是在需要高可用性、高性能和安全性的场景。以下是对 Oracle 数据库的详细介绍&#xff0c;包括它的各个方面。 一、Ora…...

VS自定义静态库并在其他项目中使用

1、VS创建一个空项目或者静态库项目 2、右键项目 属性 修改生成文件类型 3、生成解决方案 4、复制.h文件和.lib文件作为静态库 5、创建一个新项目 测试使用新生成的静态库 在新项目UseStaticLib中加一个新文件夹lib&#xff0c;lib中放入上面的.h和.lib文件。 6、vs中右…...

5G AAU(Active Antenna Unit)详细介绍

5G AAU&#xff08;Active Antenna Unit&#xff09;详细介绍 1. 定义与架构 5G AAU&#xff08;Active Antenna Unit&#xff0c;有源天线单元&#xff09;是5G无线基站系统中的核心组件&#xff0c;它集成了射频&#xff08;RF&#xff09;和天线功能&#xff0c;是4G时代R…...

力扣32.最长有效括号(栈)

32. 最长有效括号 - 力扣&#xff08;LeetCode&#xff09; 代码区&#xff1a; #include<stack> #include<string> /*最长有效*/ class Solution { public:int longestValidParentheses(string s) {stack<int> st;int ans0;int ns.length();st.push(-1);fo…...

【计算机网络中的奈氏准则与香农定理】

文章目录 一、前言二、奈氏准则1. 概念2. 奈氏准则公式3. 奈氏准则的意义 三、香农定理1. 概念2. 香农定理公式3. 香农定理的意义 四、奈氏准则与香农定理的对比五、应用示例1. 奈氏准则示例2. 香农定理示例 六、总结 一、前言 在计算机网络中&#xff0c;数据的传输速率与信道…...

vue3 项目中预览 word(.docx)文档方法

vue3 项目中预览 word&#xff08;.docx&#xff09;文档方法 通过 vue-office/docx 插件预览 docx 文档通过 vue-office/excel 插件预览 excel 文档通过 vue-office/pdf 插件预览 pdf 文档 安装插件 npm install vue-office/docx vue-demi示例代码 <template><Vu…...

DHCP(Dynamic Host Configuration Protocol)原理深度解析

目录 一、DHCP 核心功能 二、DHCP 工作流程&#xff08;四阶段&#xff09; 三、关键技术机制 1. 中继代理&#xff08;Relay Agent&#xff09; 2. Option 82&#xff08;中继信息选项&#xff09; 3. 租期管理 4. 冲突检测 四、DHCP 与网络架构交互 1. MLAG 环境 2.…...

创建login.api.js步骤和方法

依次创建 login.api.js、home.api.js...... login.api.js、home.api.js 差不多 导入到 main.js main.js 项目中使用...

基于springboot二手交易平台(源码+lw+部署文档+讲解),源码可白嫖!

摘要 人类现已迈入二十一世纪&#xff0c;科学技术日新月异&#xff0c;经济、资讯等各方面都有了非常大的进步&#xff0c;尤其是资讯与网络技术的飞速发展&#xff0c;对政治、经济、军事、文化等各方面都有了极大的影响。 利用电脑网络的这些便利&#xff0c;发展一套二手交…...

帕金森患者的生活重塑:从 “嘴” 开启康复之旅

当提到帕金森病&#xff0c;许多人会联想到震颤、僵硬和行动迟缓等症状。这种神经系统退行性疾病&#xff0c;给患者的生活带来了巨大的挑战。然而&#xff0c;你可知道&#xff0c;帕金森患者恢复正常生活&#xff0c;可以从 “嘴” 开始管理&#xff1f; 帕金森病在全球影响着…...

相生、相克、乘侮、复杂病机及对应的脏腑功能联系

一、五行相生关系&#xff08;母子关系&#xff09; 五行生序脏腑关系生理表现举例木生火肝&#xff08;木&#xff09;滋养心&#xff08;火&#xff09;肝血充足则心血旺盛火生土心&#xff08;火&#xff09;温煦脾&#xff08;土&#xff09;心阳充足则脾胃运化功能正常土…...

鸿蒙OS 5 架构设计探秘:从分层设计到多端部署

文章目录 鸿蒙OS架构设计探秘&#xff1a;从分层设计到多端部署一、鸿蒙的分层架构设计二、模块化设计的精髓三、智慧分发设计&#xff1a;资源的动态调度四、一次开发&#xff0c;多端部署的实践总结与思考 鸿蒙OS架构设计探秘&#xff1a;从分层设计到多端部署 最近两年来&a…...

5. 实现一个中间件

原文地址: 实现一个中间件 更多内容请关注&#xff1a;php代码框架 理解中间件 中间件&#xff08;Middleware&#xff09; 是一种在请求被路由到控制器方法之前或响应返回客户端之前执行的代码。它通常用于处理通用任务&#xff0c;如身份验证、日志记录、CORS 处理等。 在…...

JVM 为什么不使用引用计数算法?——深入解析 GC 策略

在 Java 中&#xff0c;垃圾回收&#xff08;Garbage Collection, GC&#xff09;是一个至关重要的功能&#xff0c;它能够自动管理内存&#xff0c;回收不再使用的对象&#xff0c;从而防止内存泄漏。然而&#xff0c;在垃圾回收的实现上&#xff0c;JVM 并未采用引用计数算法…...