嵌套类还是非嵌套类?

时间:2010-03-13 19:52:33

标签: c++ scheduler nested-class

我有A类和A对象列表。 A具有应该每X秒执行一次的函数f(对于第一个实例每1秒执行一次,对于秒实例每5秒执行一次等)。 我有一个调度程序类负责在正确的时间执行函数。 我想做的是创建一个新类ATime,它将ptr保存到A实例,并且应该执行时间A :: f。调度程序将保留Atime的最小优先级队列。

  1. 您认为这是正确的实施吗?
  2. ATime应该是调度程序的嵌套类吗?

4 个答案:

答案 0 :(得分:4)

根据您的描述,听起来它可以起作用: - )

IMHO类ATime比调度程序更多地属于调度程序。调度程序必须完成其工作,并且A不需要它。事实上,A(以及世界其他地方)甚至不需要知道它的存在 - 所以把它作为调度程序的私有嵌套类对我来说是合适的。

答案 1 :(得分:1)

这可能有点过于先进,但这里有......

boost::functionboost::bind可用于实现一个不需要了解A类的调度程序。这将使您的调度程序更具通用性和可重用性。

以下是一些示例代码,说明了如何在您的案例中使用这些Boost工具:

#include <ctime>
#include <queue>
#include <boost/function.hpp>
#include <boost/bind.hpp>

struct Foo
{
    void onScheduler(time_t time) {/*...*/}
};

struct Bar
{
    void onScheduler(time_t time) {/*...*/}
};

typedef boost::function<void (time_t)> SchedulerHandler;

struct SchedulerEvent
{
    bool operator<(const SchedulerEvent& rhs) const {return when < rhs.when;}

    SchedulerHandler handler;
    time_t when;
};

class Scheduler
{
public:
    void schedule(SchedulerHandler handler, time_t when)
    {
        SchedulerEvent event = {handler, when};
        queue_.push(event);
    }

private:
    std::priority_queue<SchedulerEvent> queue_;
    void onNextEvent()
    {
        const SchedulerEvent& next = queue_.top();
        next.handler(next.when);
        queue_.pop();
    }
};

int main()
{
    Scheduler s;
    Foo f1, f2;
    Bar b1, b2;

    time_t now = time(0);
    s.schedule(boost::bind(&Foo::onScheduler, &f1, _1), now + 1);
    s.schedule(boost::bind(&Foo::onScheduler, &f2, _1), now + 2);
    s.schedule(boost::bind(&Bar::onScheduler, &b1, _1), now + 3);
    s.schedule(boost::bind(&Bar::onScheduler, &b2, _1), now + 4);

    // Do scheduling...

    return 0;
}

请注意,SchedulerFoo&amp; Bar,反之亦然。所有Scheduler真正想要的是一个“回调”仿函数,它与SchedulerHandler指定的签名相匹配。

如果您需要取消SchedulerEvent,事情会变得有点复杂,因为boost::function个对象无法比较。要解决这个问题,您需要在注册事件时返回某种“连接”标记。这基本上就是Boost.Signal所做的。

希望这有帮助。

答案 2 :(得分:0)

这种类最好是在调度程序类中嵌套的私有结构,因此您可以轻松访问调度程序类中的所有字段。 (默认情况下,结构的所有字段都是公共的。)

答案 3 :(得分:0)

至于第二部分(以及标题中的问题),IMO完全是品味问题。您也可以选择减少Scheduler类定义中的混乱,并将ATime放在带有警告名称(如detail)的子名称空间中,以防止人们使用它。毕竟,如果它只对调度程序有用,那么就没有太多需要隐藏它 - 无论如何都没有人想要使用它。

也许它在C ++ 0x中可能有所不同(我想我已经听过一些关于它如何改变嵌套类和父类之间的可访问性规则的传言,或者说,在这种情况下,嵌套可能更值得)。 / p>

对于通用性,您可能还想使用模板,最后可能会使用Scheduler<A>(使用TimedOperation<A>)(或者无数的潜在改进/概括)?