C++动态分配内存知识点!

个人主页:PingdiGuo_guo

收录专栏:C++干货专栏

大家好呀,又是分享干货的时间,今天我们来学习一下动态分配内存。

文章目录

1.动态分配内存的思想

2.动态分配内存的概念

2.1内存分配函数

2.2动态内存的申请和释放

2.3内存碎片问题

3.动态分配内存的作用

3.1 灵活分配内存空间

3.2 提高内存利用率

3.3 动态数据结构的实现

3.4 避免内存溢出和内存泄漏

3.5 提高程序的性能

3.6 总结

4.动态分配内存的实现

4.1 步骤

4.1.1 确定需要分配的内存大小

4.1.2 使用new操作符分配内存

4.1.3 检查分配是否成功

4.1.4 使用分配的内存

4.2 代码示例

5.动态分配内存的分类及代码

5.1 动态分配单个对象的内存

5.1.1 介绍

5.1.2 代码示例

5.2 动态分配对象数组的内存

5.2.1 介绍

5.2.2 代码示例

5.3 注意事项

6.动态分配内存的练习

6.1 题目描述

6.2 知识点

6.3 步骤

6.3.1 初始化

6.3.2 输入数组大小

6.3.3 分配内存

6.3.4 输入字符串内容

6.3.5 显示字符串内容

6.3.6 用户选择

6.3.7 释放内存

6.3.8 结束程序

6.4 代码

7.总结


1.动态分配内存的思想

动态分配内存是指在程序运行时根据需要动态地分配内存空间。这相对于静态分配内存来说,静态分配内存是在编译时固定地分配内存空间,而动态分配内存可以在程序运行期间根据实际需求进行内存的申请和释放,以提高内存的利用率和灵活性。

2.动态分配内存的概念

动态分配内存的概念包括以下几个方面:

2.1内存分配函数

动态分配内存需要使用内存分配函数,如C语言中的malloc()、calloc()、realloc()等,这些函数可以根据需要在运行时动态地分配一块连续的内存空间。

2.2动态内存的申请和释放

使用内存分配函数可以申请一块指定大小的内存空间,申请的内存空间可以在程序运行期间使用。使用完毕后,可以使用释放函数将内存空间释放,以便其他程序继续使用。

2.3内存碎片问题

动态分配内存可能会导致内存碎片问题。当频繁地进行内存分配和释放操作时,可能会在内存中留下一些未被使用的小块内存,这些小块内存无法被再次利用,导致内存的浪费。为了解决内存碎片问题,可以使用内存管理算法来进行内存的分配和释放操作。

3.动态分配内存的作用

动态分配内存在计算机编程中有很多重要的作用,包括:

3.1 灵活分配内存空间

动态分配内存可以根据程序的实际需求,在运行时动态地申请适当大小的内存空间。这使得程序可以根据具体情况来分配所需的内存,提高了程序的灵活性和适应性。

3.2 提高内存利用率

动态分配内存可以避免静态分配内存的固定大小限制,可以根据实际需要进行灵活的内存分配。这样可以更有效地利用内存资源,避免了内存的浪费。

3.3 动态数据结构的实现

动态分配内存是实现动态数据结构(如链表、树等)的基础。动态数据结构的大小可能在程序运行过程中变化,需要动态地为其分配和释放内存空间。

3.4 避免内存溢出和内存泄漏

动态分配内存可以避免程序因为内存空间不足而导致的内存溢出错误。同时,使用动态分配内存还可以确保内存的正确释放,避免造成内存泄漏问题。

3.5 提高程序的性能

动态分配内存可以减少内存碎片的问题,提高内存的利用效率。同时,动态分配内存也可以减少静态分配内存的开销,提高程序的性能。

3.6 总结

总之,动态分配内存在计算机编程中具有重要的作用,它可以提供灵活的内存分配方式,提高内存的利用率,支持动态数据结构的实现,避免内存溢出和内存泄漏问题,同时提高程序的性能。

4.动态分配内存的实现

在C++中,动态内存分配通常使用new和delete操作符来完成。下面我将分步骤和代码两部分来介绍如何进行动态内存分配。



4.1 步骤

4.1.1 确定需要分配的内存大小

首先,你需要确定要分配多少内存。这通常取决于你要存储的数据类型以及你要存储多少这样的数据。


4.1.2 使用new操作符分配内存

使用new操作符来分配内存。例如,如果你要分配一个整数数组,你可以使用new int[size],其中size是你想要的数组大小。


4.1.3 检查分配是否成功

new操作符在无法分配所需内存时会返回nullptr。因此,你应该检查返回的指针是否为nullptr,以确保内存已成功分配。


4.1.4 使用分配的内存

一旦内存成功分配,你就可以开始使用它。例如,你可以将值存储在数组中,或者创建对象等。
释放内存:当你不再需要分配的内存时,应使用delete或delete[]操作符来释放它。忘记释放内存会导致内存泄漏,这是一个常见的编程错误。


4.2 代码示例


下面是一个简单的代码示例,演示了如何在C++中动态分配和释放内存:

 

#include <iostream>int main() {
// 步骤1:确定需要分配的内存大小
const int size = 10;// 步骤2:使用new操作符分配内存
int* array = new int[size];// 检查分配是否成功
if (array == nullptr) {
std::cerr << "Memory allocation failed!" << std::endl;
return 1; // 返回错误代码
}// 步骤3:使用分配的内存
for (int i = 0; i < size; ++i) {
array[i] = i;
}// 打印数组内容
for (int i = 0; i < size; ++i) {
std::cout << array[i] << " ";
}
std::cout << std::endl;// 步骤4:释放内存
delete[] array;return 0;
}


在这个示例中,我们首先确定要分配的内存大小(一个包含10个整数的数组)。然后,我们使用new操作符分配内存,并检查是否成功。接着,我们使用分配的内存来存储值,并打印数组的内容。最后,我们使用delete[]操作符来释放内存。

5.动态分配内存的分类及代码

在C++中,动态内存分配可以分为两类:动态分配单个对象的内存和动态分配对象数组的内存。



5.1 动态分配单个对象的内存


当你知道需要创建一个对象,但不知道它的生命周期时,可以使用new操作符动态地为其分配内存。这种分配方式在对象的大小不是固定大小时特别有用。



5.1.1 介绍


使用new为单个对象分配内存时,你需要指定对象的类型。new会返回指向新创建对象的指针。如果内存分配成功,你可以使用这个指针来访问和操作对象。如果内存分配失败,new会返回nullptr。



5.1.2 代码示例

 

#include <iostream>class MyClass {
public:
MyClass(int value) : value_(value) {}
void printValue() { std::cout << value_ << std::endl; }
private:
int value_;
};int main() {
// 动态分配单个对象的内存
MyClass* obj = new MyClass(42);// 使用对象
obj->printValue();// 释放内存
delete obj;return 0;
}


5.2 动态分配对象数组的内存


当你需要创建多个同类型的对象时,可以使用new操作符来动态分配一个对象数组。这种方式在你不确定数组大小,或者数组大小在运行时才能确定时非常有用。



5.2.1 介绍



使用new为对象数组分配内存时,你需要指定对象的类型和数组的大小。new会返回一个指向数组第一个元素的指针。与单个对象不同,当你使用new为数组分配内存时,需要使用delete[]来释放内存。



5.2.2 代码示例

 

#include <iostream>class MyClass {
public:
MyClass(int value) : value_(value) {}
void printValue() { std::cout << value_ << std::endl; }
private:
int value_;
};int main() {
// 动态分配对象数组的内存
const int arraySize = 5;
MyClass* array = new MyClass[arraySize];// 初始化数组中的对象
for (int i = 0; i < arraySize; ++i) {
array[i] = MyClass(i * 10);
}// 使用数组中的对象
for (int i = 0; i < arraySize; ++i) {
array[i].printValue();
}// 释放内存
delete[] array;return 0;
}


在上面的示例中,我们动态地创建了一个包含5个MyClass对象的数组,并分别初始化了它们。之后,我们遍历数组并打印每个对象的值。最后,我们使用delete[]释放了整个数组所占用的内存。



5.3 注意事项

1.使用new分配的内存必须使用delete或delete[]来释放,否则会导致内存泄漏。
2.new和delete是配对使用的,new[]和delete[]也是配对使用的。不应该混合使用它们,因为这会导致未定义的行为。
3.在使用new分配内存后,总是应该检查返回的指针是否为nullptr,以确保内存分配成功。
4.在C++11及以后的版本中,推荐使用智能指针(如std::unique_ptr和std::shared_ptr)来管理动态分配的内存,以自动处理内存释放,减少内存泄漏的风险。

6.动态分配内存的练习

6.1 题目描述



创建一个程序,该程序使用动态内存分配来创建一个字符串数组。用户将首先输入数组的大小,然后为每个字符串元素输入具体的字符串内容。程序将显示所有输入的字符串,并允许用户选择是否继续添加更多字符串或释放内存并退出程序。


6.2 知识点



动态内存分配与释放(new、delete[])
字符串处理(std::string):C++字符串详解
用户输入和输出(std::cin、std::cout)
循环结构(while、for):C++循环:简化重复的代码
条件语句(if、else):C++分支语句


6.3 步骤



6.3.1 初始化

设置必要的变量和标志,如数组大小、当前索引、是否继续的标志等。



6.3.2 输入数组大小

提示用户输入字符串数组的大小,并读取输入。



6.3.3 分配内存

使用new[]为字符串数组分配内存。



6.3.4 输入字符串内容

使用循环让用户为每个数组元素输入字符串内容。



6.3.5 显示字符串内容

使用循环显示所有输入的字符串。



6.3.6 用户选择

提供选项让用户决定是否继续添加字符串或退出程序。



6.3.7 释放内存

如果用户选择退出,释放已分配的内存。



6.3.8 结束程序

退出程序。



6.4 代码

 

#include <iostream>
#include <string>int main() {
int size;
std::cout << "Enter the size of the string array: ";
std::cin >> size;if (size <= 0) {
std::cerr << "Invalid array size. Size must be a positive integer." << std::endl;
return 1;
}std::string* arr = new std::string[size];
if (arr == nullptr) {
std::cerr << "Memory allocation failed!" << std::endl;
return 1;
}// 输入字符串内容
std::cout << "Enter " << size << " strings for the array:" << std::endl;
for (int i = 0; i < size; ++i) {
std::cin >> arr[i];
}// 显示字符串内容
std::cout << "The array contents are:" << std::endl;
for (int i = 0; i < size; ++i) {
std::cout << arr[i] << std::endl;
}// 用户选择
char choice;
do {
std::cout << "Do you want to continue adding more strings? (y/n): ";
std::cin >> choice;
std::cin.ignore(); // 忽略换行符if (choice == 'y' || choice == 'Y') {
// 如果用户选择继续,再次分配内存并输入字符串
size *= 2; // 假设我们每次翻倍
std::string* newArr = new std::string[size];
for (int i = 0; i < size / 2; ++i) {
newArr[i] = arr[i];
}
delete[] arr;
arr = newArr;std::cout << "Enter " << size / 2 << " additional strings:" << std::endl;
for (int i = size / 2; i < size; ++i) {
std::cin >> arr[i];
}// 再次显示字符串内容(可选)
// ...} else if (choice == 'n' || choice == 'N') {
// 如果用户选择退出,释放内存并退出程序
std::cout << "Exiting program." << std::endl;
break;
} else {
std::cout << "Invalid choice. Please enter 'y' or 'n': " << std::endl;
}
} while (true);// 释放内存
delete[] arr;return 0;
}


这个程序演示了如何动态分配内存来创建一个字符串数组,如何让用户输入字符串内容,如何根据用户的选择动态调整数组大小,以及如何释放内存。同时,它也展示了基本的错误处理和用户交互。

7.总结

本篇博客到这里就结束了,感谢大家的支持与观看,如果有好的建议欢迎留言,谢谢大家啦!

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

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

相关文章

⭐北邮复试刷题LCR 018. 验证回文串__双指针 (力扣119经典题变种挑战)

LCR 018. 验证回文串 给定一个字符串 s &#xff0c;验证 s 是否是 回文串 &#xff0c;只考虑字母和数字字符&#xff0c;可以忽略字母的大小写。 本题中&#xff0c;将空字符串定义为有效的 回文串 。 示例 1: 输入: s “A man, a plan, a canal: Panama” 输出: true 解释…

如何选择护眼台灯?孩子学习必选五大宝藏台灯推荐!

因为护眼台灯能提供充足明亮的光照&#xff0c;以及很好的保护眼睛预防近视效果&#xff0c;所以现在的儿童青少年书桌上都会有一盏护眼台灯。但是也有很多家长为孩子选择护眼台灯后&#xff0c;反馈护眼台灯的质量参差不齐&#xff0c;很难避免会购买到劣质产品&#xff0c;这…

2023年12月 Python(五级)真题解析#中国电子学会#全国青少年软件编程等级考试

Python等级考试(1~6级)全部真题・点这里 一、单选题(共25题,共50分) 第1题 下面代码的输出结果是?( ) dict1 = {1: 10, 2: 20, 3: 30} dict2 <

【安卓基础1】初识Android

&#x1f3c6;作者简介&#xff1a;|康有为| &#xff0c;大四在读&#xff0c;目前在小米安卓实习&#xff0c;毕业入职 &#x1f3c6;本文收录于 安卓学习大全&#xff0c;欢迎关注 &#x1f3c6;安卓学习资料推荐&#xff1a; 视频&#xff1a;b站搜动脑学院 视频链接 &…

Git笔记——2

提示&#xff1a;文章写完后&#xff0c;目录可以自动生成&#xff0c;如何生成可参考右边的帮助文档 文章目录 前言 一、撤销修改__情况一 二、撤销修改__情况二 三、撤销修改__情况三 四、删除文件 五、理解分支 六、创建、切换和合并分支初体验 七、删除分支 八、合并冲突 总…

idea maven创建kotlin项目

第一步&#xff1a;打开idea 第二步&#xff1a;添加依赖 <repositories><repository><id>mavenCentral</id><url>https://repo1.maven.org/maven2/</url></repository></repositories><build><sourceDirectory>…

ElasticSearch DSL查询、排序 、分页的原理及语法

1. DSL查询分类和基本语法 ElasticSearch提供了基于Json的DSL来定义查询&#xff0c;常见的查询类型包括&#xff1a; • 查询所有&#xff1a;查询出所有数据&#xff0c;一般测试用&#xff0c;一般不是查出所有&#xff0c;一次性查询20条。例如 match_all • 全文检索(ful…

【webrtc】m77 PacedSender

mediasoup是m77的代码,m77的代码并没有paced controller ,而且与paced sender 的逻辑混在了一起。结合大神们的代码分析,对照m77 进行 理解。m77 有ProbeController。给pacersender 更新飞行数据:PacedSender::InsertPacket(size_t bytes) 对应的是 PacingController::OnPa…

虹科技术丨PTP时钟源设备全攻略:从普通时钟到透明时钟的进阶之路

来源&#xff1a;虹科工业智能互联 虹科技术丨PTP时钟源设备全攻略&#xff1a;从普通时钟到透明时钟的进阶之路 原文链接&#xff1a;https://mp.weixin.qq.com/s/ArBtuLpU6mXax4QWmZDKfQ 欢迎关注虹科&#xff0c;为您提供最新资讯&#xff01; #PTP #普通时钟 #透明时钟 …

区块链笔记(五)---德勤相关分析报告

web3.0 定义&#xff1a; 在《Insights into a Modern World》提出&#xff0c;“信息将由用户自己发布、保管、不可追溯且永远不会泄露&#xff0c;用户的任何行为将不需要任何中间机构来帮助传递”&#xff1b;用来指代一种区块链技术&#xff0c;可以基于“无须信任的交互…

解决用户留存难!复购低! 作为企业家的你可以看看!

工会排队模式详解 在互联网营销的大潮中&#xff0c;各种促销模式层出不穷&#xff0c;但真正能够吸引消费者并实现双赢的却寥寥无几。工的会排队模式便是在这一背景下应运而生&#xff0c;它巧妙地结合了工会积分、奖金池和排队机制&#xff0c;为消费者和商家带来了全新的体…

助力探索社交出海最短变现路径,融云 1V1 音视频「限时免费」

在社交赛道&#xff0c;1V1 业务是最好的切入点。 对于初创公司来说&#xff0c;1V1 业务的技术成本和运营成本相对可控&#xff0c;并且具备与秀场直播等业务融合拓展的巨大空间。未来&#xff0c;相信 1V1 业务会吸引更多开发者投身其中。 一位社交出海经验丰富的从业者曾在…

PHP+vue+mysql校园论坛bbs系统w076f-

本文尝试以B/S架构设计模式中的vue框架&#xff0c;php语言为基础&#xff0c;通过必要的编码处理、BBS论坛系统整体框架、功能服务多样化和有效性的高级经验和技术实现方法&#xff0c;旨在完成一个快速、高效、便捷的BBS论坛系统。本系统以用户与管理员两类人&#xff0c;作为…

【力扣 - 二叉树的直径】

题目描述 给你一棵二叉树的根节点&#xff0c;返回该树的 直径 。 二叉树的 直径 是指树中任意两个节点之间最长路径的 长度 。这条路径可能经过也可能不经过根节点 root 。 两节点之间路径的 长度 由它们之间边数表示。 提示&#xff1a; 树中节点数目在范围 [1, 10000] 内…

【最新Dubbo3深入理解】Dubbo3核心Tripple协议详解

欢迎关注公众号&#xff08;通过文章导读关注&#xff1a;【11来了】&#xff09;&#xff0c;及时收到 AI 前沿项目工具及新技术的推送&#xff01; 在我后台回复 「资料」 可领取编程高频电子书&#xff01; 在我后台回复「面试」可领取硬核面试笔记&#xff01; 文章导读地址…

区块链游戏解说:什么是 Planet IX

作者&#xff1a;lesleyfootprint.network 编译&#xff1a;cicifootprint.network 数据源&#xff1a;Planet IX Dashboard 什么是 Planet IX Planet IX&#xff0c;一个由原生 IX TOKEN 推动的 Web3 玩赚平台。作为一款 GameFi 策略游戏&#xff0c; Planet IX 上的每项资…

C语言字符串函数strchr与strrchr

注意&#xff1a; 这两个函数的功能&#xff0c;都是在指定的字符串 s 中&#xff0c;试图找到字符 c。strchr() 从左往右找&#xff0c;strrchr() 从右往左找。字符串结束标记 ‘\0’ 被认为是字符串的一部分。 示例 char *p;p strchr("www.qq.com", .); // 从左…

python自动化接口测试

前几天&#xff0c;同组姐妹说想要对接口那些异常值进行测试&#xff0c;能否有自动化测试的方法。仔细想了一下&#xff0c;工具还挺多&#xff0c;大概分析了一下&#xff1a; 1、soapui:可以对接口参数进行异常值参数化&#xff0c;可以加断言&#xff0c;一般我们会加http…

如何申请试用Gemini 1.5 Pro

https://developers.googleblog.com/2024/02/gemini-15-available-for-private-preview-in-google-ai-studio.html 我开发的chatgpt网站&#xff1a; https://chat.xutongbao.top

浅谈数字信号处理器的本质与作用:从定义、原理到应用场景

数字信号处理器&#xff08;DSP&#xff09;作为一种关键的电子元件&#xff0c;在通信、音频、图像处理等领域扮演着不可或缺的角色。然而&#xff0c;对于许多人来说&#xff0c;数字信号处理器的概念可能依然模糊&#xff0c;其作用和原理也许并不为人所熟知。因此&#xff…