C++ C++;在函数-新手问题中分配动态内存
我正在调查内存泄漏,据我所见,问题如下:C++ C++;在函数-新手问题中分配动态内存,c++,memory,function,dynamic,pointers,C++,Memory,Function,Dynamic,Pointers,我正在调查内存泄漏,据我所见,问题如下: int main(){ char *cp = 0; func(cp); //code delete[] cp; } void func(char *cp){ cp = new char[100]; } 在//code注释中,我希望cp指向分配的内存,但它仍然是一个空指针,这意味着我从未删除内存。我在写什么?参数cp是函数的局部变量-更改它不会改变函数之外的任何内容。编写函数的更好方法是: char * func
int main(){
char *cp = 0;
func(cp);
//code
delete[] cp;
}
void func(char *cp){
cp = new char[100];
}
在//code注释中,我希望cp指向分配的内存,但它仍然是一个空指针,这意味着我从未删除内存。我在写什么?参数cp是函数的局部变量-更改它不会改变函数之外的任何内容。编写函数的更好方法是:
char * func(){
return new char[100];
}
不要直接回答您的问题,但您可能应该使用std::string和std::vector,而不是动态分配的数组。您正在分配
cp
分配内存的值。然而,这是堆栈上的一个变量:main中cp
的副本cp
是您所在函数的本地值
您需要的是参考资料:
void func(char *& cp)
这将别名
cp
作为传入的参数。您传入的是cbuf
,而不是cp
void func(char *cp){
cp = new char[100];
}
在这个函数中,char*cp是一个“指针通过复制”这意味着它们指向相同的内存地址,但它们不是相同的指针。当您更改内部指针,使其指向其他位置时,传递的原始指针将一直指向0。该函数仅更改
cp
的副本。请使用参考资料。正如GMan和Neil所提到的,为了工作,您必须将func更改为:
char*func()代码>
或void func(char*&p)代码>
这将解决你眼前的问题
然而,存在一个维护问题。在这两种情况下,func都返回一个指针。func用户不清楚的是,返回的指针必须删除。因此,除非100%必要,否则通常避免这种构造。而是:
帮助用户分配可传递给func的正确内存量
使用对象存储分配的内存。然后,对象可以在销毁字符数组时删除该字符数组
<对于C++代码,我建议:
class CBuf
{
public
CBuf()
{
iBuf = new char[100];
}
~CBuf
{
delete[] iBuf;
}
char* func()
{
//do stuff;
return iBuf;
}
private:
char* iBuf;
};
int main()
{
CBuf cb;
char* mychar = cb.func();
//do stuff with character array
//destructor gets called here because cb goes out of scope
}
然而,特别是在C编程中,可能100%需要使用某种排序函数来创建数组。因此,在C编程中,可以用CreateCBuf
和destroucCBUF
函数替换析构函数。通过这种方式,库的用户将知道返回的缓冲区需要销毁。尽管引用提供了直观的抽象,并通过C++11右值引用进一步增强,以允许函数链接(和其他深奥的编码),但它们是否提供了任何安全性(即
在某些情况下,最好使用指针到指针函数参数来解决上述问题。
特别是当需要在ANSI C和C++中保持类似的代码库时。p>
#include <iostream>
using namespace std;
void func(char ** cp) {
*cp = new char[100];
//do something useful
(*cp)[0] = 'A';
}
void func(char *& cp) {
cp = new char[100];
//do something useful
cp[0] = 'B';
}
int main(int argc, char** argv) {
char * cp;
//pointer to pointer
func(&cp);
cout << "Index 0 : " << cp[0] << '\n' << flush;
delete[] cp; //remember to delete!!
//pointer to ref
func(cp);
cout << "Index 0: " << cp[0] << '\n' << flush;
delete[] cp;
return 0;
}
#包括
使用名称空间std;
无效函数(字符**cp){
*cp=新字符[100];
//做些有用的事
(*cp)[0]=“A”;
}
无效函数(字符*&cp){
cp=新字符[100];
//做些有用的事
cp[0]=“B”;
}
int main(int argc,字符**argv){
char*cp;
//指针到指针
func&cp;
我能假设cbuf
应该是cp
吗?定位真实的代码怎么样。除非代码被剪切粘贴,否则你可能会添加错误。这只会让事情变得更困难,我们最终会解决像cbuf->cpSorry这样的剪切粘贴错误。关于这一点,我下次会记住。是的,cbuf应该是c即使他通过了CP,它也会指向0个//码,这也没关系,因为你也通过值传递。嗯,两个下票。我不特别在乎,但是其他人可能从知道这个答案的错误中受益。我看不到任何东西。如果你要指出一些类似C++的特性。另外,如果你打算使用那些特殊的功能,你可能想通过引用传递一个指向其中一个的指针来创建它,或者通过引用传递一个已经创建的指针来避免复制构造函数的惩罚……但是实际上,没有什么比这更重要的了用这个答案,指针没有复制构造函数。我指的是STD::String和STD::vector,当提到“C++的特性时,你说”。我把我的回答弄得一团糟,很抱歉,你有什么,我会加上“不要硬代码…”。剩下的是指“C++特性”。vector很好。它为您处理所有内存管理。OPs示例中的问题是所有权非常不明确。