C++ 如何在没有默认构造函数和堆使用的情况下初始化对象?
在编写没有MMU的嵌入式系统时,我不应该使用heap(因为内存碎片问题)C++ 如何在没有默认构造函数和堆使用的情况下初始化对象?,c++,embedded,C++,Embedded,在编写没有MMU的嵌入式系统时,我不应该使用heap(因为内存碎片问题) 部分软件用C语言编写(驱动程序),逻辑在C++子集中编写,无需动态分配内存。 由于单元测试,默认构造函数被删除。相反,有一个单参数构造函数引用驱动程序函数指针的结构 driver.h:(纯C模块) #pragma一次 bool Init(); uint32_t ReadMeasurement(); 模块.HPP:< /St>(C++部分) 类模块{ 公众: DriverApi结构{ 无效(*Init)(); uint3
部分软件用C语言编写(驱动程序),逻辑在C++子集中编写,无需动态分配内存。 由于单元测试,默认构造函数被删除。相反,有一个单参数构造函数引用驱动程序函数指针的结构
driver.h:(纯C模块)#pragma一次
bool Init();
uint32_t ReadMeasurement();
<强>模块.HPP:< /St>(C++部分)
类模块{
公众:
DriverApi结构{
无效(*Init)();
uint32_t(*ReadData)();
};
模块()=删除;
显式模块(DriverApi和aDriverApi);
私人:
DriverApi&mDriverApi;
};
模块管理器:
模块管理器。hpp:
类模块管理器{
// (...)
私人:
Module::DriverApi Module_1;//我不能用这种方式声明它
Module::DriverApi Module_2;//因为缺少默认构造函数。
模块::DriverApi模块_3;
等
};
如何在不使用堆的情况下初始化模块1
、模块2
和模块3
?和n
参数构造函数
我知道的选项:
- 它看起来很容易使用
,但是std::shared_ptr
使用堆std::make_shared
- 我可以离开默认构造函数,然后调用Init(Module::DriverApi*aDriverApi)之类的函数,但这“违反”了RAII
是否有其他方法可以创建“优雅”的嵌入式安全初始化?使用默认构造函数或使用命名参数编写构造函数。如果需要将成员初始化为非零值,但由于构造函数的参数太少而无法访问这些值,则构造函数的设计不正确 由于单元测试,默认构造函数被删除 测试应该是为了使产品更好——如果它们做的相反,就把它们扔掉 通常,任何嵌入式系统都有一组固定的驱动程序。所以通常情况下,将它们作为非静态成员是没有意义的。为每个硬件外围设备提供一个驱动程序类是有意义的。然后为目标上存在的该硬件的每个实例创建一个
静态
实例。您不需要涵盖永远不会出现的硬件,也不需要在运行时动态更改硬件。事实上,它的很大一部分应该是常量,并存储在闪存中
RAII在单核、单进程嵌入式系统上的使用有限,因为您的程序需要确定性,并且它拥有MCU上的所有资源。您通常不需要释放任何东西,您所需要的只是分配产品所需的内存
保持简单。不要发明毫无意义的抽象层。我只是把代码放在IDE中,然后编译。 我可以在您的计划中确定的内容:
bool Init()代码>到void(*Init)(
,请更改返回类型
class Module {
public:
struct DriverApi {
void (*Init)();
uint32_t (*ReadData)();
};
Module() = delete;
explicit Module(DriverApi &aDriverApi):mDriverApi{aDriverApi}{}
private:
DriverApi& mDriverApi;
};
void fun(){
std::cout<<"This is fun\n";
}
int main(){
Module::DriverApi module_1; // I can't declare this in this way because of lack of default constructor.
module_1.Init = fun;
module_1.Init();
Module m{module_1};
return 0;
}
类模块{
公众:
DriverApi结构{
无效(*Init)();
uint32_t(*ReadData)();
};
模块()=删除;
显式模块(DriverApi和aDriverApi):mDriverApi{aDriverApi}{}
私人:
DriverApi&mDriverApi;
};
虚无乐趣(){
std::coutFirst定义一个DriveApi
对象,然后用它定义Module
对象?可以在任何范围内完成。我不确定我是否理解这个问题。Module::DriverAPI d;//使用d执行操作;模块m(d);
?如果你的类没有默认构造函数,你需要调用另一个构造函数。你能解释一下为什么你认为你需要堆吗?(不清楚你想解决什么问题,更不用说你想解决什么问题了)将mDriverApi
作为引用似乎有些奇怪。说来没错,但这确实让我想知道为什么。关于更新的编辑。Module::DriverApi Module_1;
很好。这是一个类成员声明,而不是实际的定义。这里没有初始化任何内容。它在ModuleManager
的构造函数中如果你真的初始化了成员。