简介: CSDN博客专家,专注Android/Linux系统,分享多mic语音方案、音视频、编解码等技术,与大家一起成长!
优质专栏:Audio工程师进阶系列【原创干货持续更新中……】🚀
优质专栏:多媒体系统工程师系列【原创干货持续更新中……】🚀
人生格言: 人生从来没有捷径,只有行动才是治疗恐惧和懒惰的唯一良药.
1.前言
本篇目的:C++之结构体使用智能指针std::unique_ptr与std::make_unique分配内存总结
2.结构体使用智能指针std::unique_ptr与std::make_unique分配内存介绍
-
在C++中,结构体(struct)是一种用户定义的数据类型,它允许我们组合多个不同类型的数据项,形成一个单一的复合数据类型。当结构体中包含动态分配的内存时,管理这些内存就变得尤为重要。std::unique_ptr和std::make_unique是C++11引入的两个智能指针工具,它们能够帮助我们自动管理这些动态分配的内存。
-
使用std::unique_ptr管理结构体内存
-
std::unique_ptr是一个独占所有权的智能指针,当指向的结构体不再需要时,unique_ptr会自动删除它,从而避免了手动调用delete的繁琐和潜在的内存泄漏问题。
-
下面是一个例子,展示如何使用std::unique_ptr来管理结构体的内存:
struct MyStruct { int x; double y; // 其他成员...
}; int main() { // 使用std::unique_ptr动态分配MyStruct对象 std::unique_ptr<MyStruct> ptr(new MyStruct{42, 3.14}); // 使用ptr std::cout << ptr->x << ", " << ptr->y << std::endl; // 当ptr离开作用域时,它所指向的MyStruct对象会被自动删除 // 不需要手动调用delete
}
-
使用std::make_unique分配结构体内存std::make_unique是一个函数模板,它用于创建一个std::unique_ptr实例,并自动分配内存。使用make_unique更加安全,因为它避免了直接使用new可能引发的异常安全性问题。
-
以下是如何使用std::make_unique来分配结构体的内存:
struct MyStruct { int x; double y; // 其他成员...
}; int main() { // 使用std::make_unique创建指向MyStruct的unique_ptr auto ptr = std::make_unique<MyStruct>(42, 3.14); // 使用ptr std::cout << ptr->x << ", " << ptr->y << std::endl; // 当ptr离开作用域时,它所指向的MyStruct对象会被自动删除
}
-
在这个例子中,我们假设MyStruct有一个接受两个参数的构造函数。std::make_unique直接调用这个构造函数来初始化MyStruct对象,并返回一个指向该对象的unique_ptr。
-
通过使用std::unique_ptr和std::make_unique,我们可以确保结构体的内存得到正确的管理,避免了手动管理内存所带来的风险和复杂性。这是现代C++编程中推荐的内存管理实践之一。
3.代码实例
<1>.v1.0 非智能指针版本
#include <iostream>
#include <memory>
#include <string>struct file {void *private_data;
};struct binder_context {int binder_context_mgr_node;const char *name;
};struct binder_proc {int proc;struct binder_context *context;
};static int binder_ioctl_set_ctx_mgr(struct file *filp){struct binder_proc *proc = (struct binder_proc *)filp->private_data;struct binder_context *context = proc->context;context->binder_context_mgr_node = 33;printf("xxx--------------->%s(), line = %d, binder_context_mgr_node = %d\n",__FUNCTION__,__LINE__,proc->context->binder_context_mgr_node);return 0;
}int main(){struct file *filp;struct binder_proc *proc = (struct binder_proc*)malloc(sizeof(struct binder_proc));proc->context = (struct binder_context*)malloc(sizeof(struct binder_context));proc->context->binder_context_mgr_node = -1;//1.初始化结构体struct filefilp = (struct file*)malloc(sizeof(struct file));// 使用 std::unique_ptr 来动态分配内存//std::unique_ptr<struct file> filp = std::make_unique<struct file>();filp->private_data = proc;//2.binder_ioctl_set_ctx_mgr(filp);printf("xxx--------------->%s(), line = %d, binder_context_mgr_node = %d\n",__FUNCTION__,__LINE__,((struct binder_proc *)(filp->private_data))->context->binder_context_mgr_node);free(proc->context);free(proc);
}
<2>.v2.0 智能指针版本
#include <iostream>
#include <memory>
#include <string>struct file {void* private_data;
};struct binder_context {int binder_context_mgr_node;const char* name;
};struct binder_proc {int proc;std::unique_ptr<binder_context> context; // 使用 std::unique_ptr 管理内存
};static int binder_ioctl_set_ctx_mgr(file* filp) {binder_proc* proc = static_cast<binder_proc*>(filp->private_data);binder_context* context = proc->context.get(); // 获取原始指针context->binder_context_mgr_node = 33;printf("xxx--------------->%s(), line = %d, binder_context_mgr_node = %d\n",__FUNCTION__,__LINE__,proc->context->binder_context_mgr_node);return 0;
}int main() {//v1.0//auto filp = std::make_unique<file>();//v2.0//std::unique_ptr<struct file> filp(new file()); // 使用 std::unique_ptr 管理内存//v3.0//std::unique_ptr<struct file> filp(std::make_unique<file>());//v4.0//std::unique_ptr<struct file> filp = std::make_unique<file>();//v5.0std::unique_ptr<struct file> filp = std::make_unique<struct file>();//std::unique_ptr<binder_proc> proc(new binder_proc());std::unique_ptr<binder_proc> proc = std::make_unique<struct binder_proc>();proc->context = std::make_unique<binder_context>(); // 使用 std::make_unique 分配内存proc->context->binder_context_mgr_node = -1;filp->private_data = proc.get();binder_ioctl_set_ctx_mgr(filp.get());printf("xxx--------------->%s(), line = %d, binder_context_mgr_node = %d\n",__FUNCTION__,__LINE__,static_cast<binder_proc*>(filp->private_data)->context->binder_context_mgr_node);// 不需要显式调用 delete,因为智能指针会在超出作用域时自动释放内存return 0;
}