【发布时间】:2017-01-05 02:08:10
【问题描述】:
我有一种情况,我在处理脉冲宽度调制的微控制器上有一门课。极其简化的例子:
class MotorDriver
{
int pin_;
public:
MotorDriver(int pin);
void init();
void start();
void stop();
void changeDutyCycle(int dc);
};
它具有初始化、启动、停止和更改pwm的功能。如果我将 4 个电机连接到微控制器,我将创建该类的 4 个实例并将它们放在一个数组中,然后调用类似的函数
motors[0].changeDutyCycle(50);
motors[1].changeDutyCycle(40);
....
出现问题是因为没有通用的方法在所述微控制器上配置定时器。例如,一台电机必须使用 Timer3,而另一台电机必须使用 Timer4。不同的定时器有不同的位大小、寄存器、通道、引脚......我希望能够为每个定时器编写自定义函数,但仍然能够将所有对象放入同一个数组并在它们上调用函数,即
class MotorDriver
{
void changeDutyCycle(int dc) = 0;
};
class MotorDriver1 : public MotorDriver
{
void changeDutyCycle(int dc)
{
TIM3->CCR2 = dc;
}
};
class MotorDriver2 : public MotorDriver
{
void changeDutyCycle(int dc)
{
TIM4->CCR1 = dc;
}
};
MotorDriver1 md1();
MotorDriver2 md2();
MotorDriver* mds[] = { &md1, &md2 };
int main()
{
mds[0]->changeDutyCycle(10);
mds[1]->changeDutyCycle(20);
}
我知道我可以通过虚函数实现我想要的。这个函数很短,而且会经常被调用,所以虚函数的价格很高。在这种情况下或不同的设计模式有没有办法避免它们?目标是拥有易于在外部使用的可重用代码。将我需要的所有东西都放在一个数组中会让很多事情变得更容易。
编辑:我知道这篇帖子Avoiding virtual functions,但与我需要的回答有关:
如果您处于每次调用的每个周期都很重要的情况,那就是 你在函数调用中做的工作很少而且你正在调用 它来自您在性能关键应用程序中的内部循环 可能需要完全不同的方法。
【问题讨论】:
-
我建议在创建新电机时使用 MotorDriver id。 ID 是一个私有变量,我们使用 ID 来访问一个定时器数组。这意味着每个计时器映射到 1 个 ID。
-
可能,计时器根本没有什么不同,而您夸大了区别对待它们的必要性?当您有 x 数量的硬件外设具有完全相同的寄存器布局时,另一种编写驱动程序的方法是类似于this,您只需将指针传递给寄存器基址偏移量。除此之外,不同计时器的驱动程序代码将 100% 相同。
标签: inheritance embedded virtual-functions