这不是我工作的实际代码。但是这段代码可以用来清楚地解释我的问题。
我有一个名为" OnCallFunction"将一些新的对象作为输入,应该在" OnCallFunction"中删除。在我应该返回的每一点上,我需要在那里添加删除代码。我认为这不是正确的做法。通过这种方式,应该记住这一点并将其放入每个将来也将要完成的回报中。如果代码不简单如下,我可能忘记插入删除部分。
#include <iostream>
#include <stdlib.h>
using namespace std;
class Student
{
public:
Student(){}
~Student(){}
int GetID(){return rand();}
};
int OnCallFunction(Student* pStudent)
{
int iValue = pStudent->GetID();
if (iValue == 5)
{
delete pStudent;
return 90;
}
if (iValue == 67)
{
delete pStudent;
return 8709;
}
if (iValue == 234)
{
delete pStudent;
return 78;
}
if (iValue == 343)
{
delete pStudent;
return 9832;
}
if (iValue == 678)
{
delete pStudent;
return 876;
}
delete pStudent;
return -1;
};
int main(int argc, const char** argv)
{
Student* pStudent = new Student();
OnCallFunction(pStudent);
};
所以,我玩了一下并开发了一个用于自动销毁堆对象的宏。 这是使用宏(AUTO_DESTROY)
的修改代码#include <iostream>
#include <stdlib.h>
using namespace std;
#define AUTO_DESTROY(ClassType, Variable, DeleteStatement)\
class AD##ClassType##Variable\
{\
public:\
AD##ClassType##Variable(ClassType* pData) {Variable=pData;};\
~AD##ClassType##Variable() {DeleteStatement;};\
private:\
ClassType* Variable;\
};\
AD##ClassType##Variable oAD##ClassType##Variable(Variable)
class Student
{
public:
Student(){}
~Student(){}
int GetID(){return rand();}
};
int OnCallFunction(Student* pStudent)
{
AUTO_DESTROY(Student, pStudent, delete pStudent);
int iValue = pStudent->GetID();
if (iValue == 5)
{
return 90;
}
if (iValue == 67)
{
return 8709;
}
if (iValue == 234)
{
return 78;
}
if (iValue == 343)
{
return 9832;
}
if (iValue == 678)
{
return 876;
}
return -1;
};
int main(int argc, const char** argv)
{
Student* pStudent = new Student();
OnCallFunction(pStudent);
};
现在我的问题是,
1) Does this has any performance/maintainability/code quality impact rather than deleting in each return?
2) In this macro it creates a class inside the function. So will than cause multiple declarations if we use the same macro, same class type, same variable name in multiple cpp files? Agree that I can test it.
3) Are there any ideas or pre-built things to do this in easier way?
NB:
请不要建议创建&#34;学生&#34;作为堆中的堆栈变量或将函数输出保存在变量中并仅在结尾处返回。 :)
答案 0 :(得分:3)
不要使用宏,也不要使用原始指针。使用unique_ptr
保存已分配的对象,并将您的功能更改为:
int OnCallFunction(std::unique_ptr<Student> pStudent)
{
int iValue = pStudent->GetID();
if (iValue == 5)
{
return 90;
}
if (iValue == 67)
{
return 8709;
}
if (iValue == 234)
{
return 78;
}
if (iValue == 343)
{
return 9832;
}
if (iValue == 678)
{
return 876;
}
return -1;
};
int main(int argc, const char** argv)
{
std::unique_ptr<Student> pStudent(new Student());
OnCallFunction(std::move(pStudent));
};
当Student
退出时,将自动完成对托管OnCallFunction()
对象的正确删除。
答案 1 :(得分:3)
提升范围退出已实施您想要的功能。您可以查看该实现或直接使用它。
示例:
#include <boost/scope_exit.hpp>
#include <cstdlib>
#include <cstdio>
#include <cassert>
int main()
{
std::FILE* f = std::fopen("example_file.txt", "w");
assert(f);
BOOST_SCOPE_EXIT(f) {
// Whatever happened in scope, this code will be
// executed and file will be correctly closed.
std::fclose(f);
} BOOST_SCOPE_EXIT_END
// Some code that may throw or return.
// ...
}
使用this功能,您几乎可以指定独立的“RAII析构函数”。
使用它可以使代码更清晰,更清晰,并避免在所有功能更容易合并(或已经存在)类的析构函数中。