具有不同行为的c++花括号

c++ curly brackets with different behaviour

本文关键字:c++      更新时间:2023-10-16

我很困惑。为什么这两个主要函数会产生不同的结果(cygwin g++)。似乎括号以某种方式2次创建PinDisplay

我认为
陈述1
陈述2
陈述3

与我认为
陈述1

陈述2
}
陈述3

// main 1
int main() {
    Simulator s;
    {
        PinDisplay d3(s.pin1, "Pin 1");
        s.run();
    }
    s.run();
    return 0;
}
/*
for = 9
Pin 1 = 1
for = 10
for = 11
for = 12
for = 13
for = 14
Pin 1 = 0
for = 15
for = 9
for = 10
for = 11
for = 12
for = 13
for = 14
for = 15
*/

// main 2
int main() {
    Simulator s;
        PinDisplay d3(s.pin1, "Pin 1");
        s.run();
    s.run();
    return 0;
}
/*
for = 9
Pin 1 = 1
for = 10
for = 11
for = 12
for = 13
for = 14
Pin 1 = 0
for = 15
for = 9
Pin 1 = 1
for = 10
for = 11
for = 12
for = 13
for = 14
Pin 1 = 0
for = 15
*/

整个代码:

观察员.h

#ifndef Observer_Pattern_Framework__
#define Observer_Pattern_Framework__
// ==== Observer Pattern Framework ============================================
#include <list>
#include <algorithm>
using namespace std;
namespace FIXUP {
//  FIXUP Needed when using BC5.02 because mem_fun is not implemented.
//  FIXUP Needed when using VC5.0 because mem_fun implementatiom in
//  function.h has problems with member functions that return void.
    template<class T>
    class mem_fun_t: public unary_function<T*, void> {
        void(T::*pmf)();
    public:
        explicit mem_fun_t(void(T::*p)()): pmf(p) {
        }
        void operator()(T* p) const {
            (p->*pmf)();
        }
    };
    template<class T> mem_fun_t<T> mem_fun(void(T::*f)()) {
        return mem_fun_t<T>(f);
    }
}
// END FIXUP
// == Observer ==
class SubjectIsDestroyed {}; // Exception
class Subject;
class Observer {
public:
    virtual void update()=0;
    virtual void destruct();
protected:
    Observer(Subject& s);
    virtual ~Observer();
    const Subject* getPointerToSubject() const  {
        if (pointerToSubject==0)
        throw SubjectIsDestroyed();
        return pointerToSubject;
    }
private:
    Subject* pointerToSubject;
    Observer(const Observer&);
    void operator=(const Observer&);
};
// == Subject ==
class Subject {
public:
    void attach(Observer* o) {
        observers.push_front(o);
    }
    void detach(Observer* o) {
        observers.remove(o);
    }
protected:
    Subject() {
    }
    virtual ~Subject() {
        using FIXUP::mem_fun;
        for_each(observers.begin(), observers.end(), mem_fun(&Observer::destruct));
    }
    void notify() const {
        using FIXUP::mem_fun;
        for_each(observers.begin(), observers.end(), mem_fun(&Observer::update));
    }
private:
    list<Observer*> observers;
    Subject(const Subject&);
    void operator=(const Subject&);
};
inline Observer::Observer(Subject& s): pointerToSubject(&s) {
    pointerToSubject->attach(this);
}
inline Observer::~Observer() {
    if (pointerToSubject)
        pointerToSubject->detach(this);
}
inline void Observer::destruct() {
    pointerToSubject->detach(this);
    pointerToSubject=0;
}
// == Model<T> ==
template <class T>
class Model: public Subject {
public:
    Model(): value(0) {
    }
    Model(const T& init): value(init) {
    }
    virtual void set(const T& v) {
        value=v;
        notify();
    }
    virtual const T& get() const {
        return value;
    }
protected:
    T value;
};
// == CallOnwrite<T, C> ==
template <class T, class C>
class CallOnWrite: public Observer {
public:
    typedef void (C::*PF)();
    CallOnWrite(Model<T>& m, C* po, PF pfu):
        Observer(m),
        pointerToComponent(po),
        pointerToUpdateFunction(pfu) {
    }
    const Model<T>& operator*() const {
        return static_cast<const Model<T>&>(*getPointerToSubject());
    }
    const Model<T>* operator->() const {
        return static_cast<const Model<T>*>(getPointerToSubject());
    }
protected:
    virtual void update() {
        (pointerToComponent->*pointerToUpdateFunction)();
    }
private:
    PF pointerToUpdateFunction;
    C* pointerToComponent;
};
#endif

测试.cpp

#include <iostream>
#include <iomanip>
#include <string>
// ==== Observer Pattern Framework ============================================
#include <list>
#include <algorithm>
using namespace std;
namespace FIXUP {
//  FIXUP Needed when using BC5.02 because mem_fun is not implemented.
//  FIXUP Needed when using VC5.0 because mem_fun implementatiom in
//  function.h has problems with member functions that return void.
template<class T>
class mem_fun_t: public unary_function<T*, void> {
    void (T::*pmf)();
public:
    explicit mem_fun_t(void (T::*p)()) :
            pmf(p) {
    }
    void operator()(T* p) const {
        (p->*pmf)();
    }
};
template<class T> mem_fun_t<T> mem_fun(void (T::*f)()) {
    return mem_fun_t<T>(f);
}
}
// END FIXUP
// == Observer ==
class SubjectIsDestroyed {
};
// Exception
class Subject;
class Observer {
public:
    virtual void update()=0;
    virtual void destruct();
protected:
    Observer(Subject& s);
    virtual ~Observer();
    const Subject* getPointerToSubject() const {
        if (pointerToSubject == 0)
            throw SubjectIsDestroyed();
        return pointerToSubject;
    }
private:
    Subject* pointerToSubject;
    Observer(const Observer&);
    void operator=(const Observer&);
};
// == Subject ==
class Subject {
public:
    void attach(Observer* o) {
        observers.push_front(o);
    }
    void detach(Observer* o) {
        observers.remove(o);
    }
protected:
    Subject() {
    }
    virtual ~Subject() {
        using FIXUP::mem_fun;
        for_each(observers.begin(), observers.end(),
                mem_fun(&Observer::destruct));
    }
    void notify() const {
        using FIXUP::mem_fun;
        for_each(observers.begin(), observers.end(),
                mem_fun(&Observer::update));
    }
private:
    list<Observer*> observers;
    Subject(const Subject&);
    void operator=(const Subject&);
};
inline Observer::Observer(Subject& s) :
        pointerToSubject(&s) {
    pointerToSubject->attach(this);
}
inline Observer::~Observer() {
    if (pointerToSubject)
        pointerToSubject->detach(this);
}
inline void Observer::destruct() {
    pointerToSubject->detach(this);
    pointerToSubject = 0;
}
// == Model<T> ==
template<class T>
class Model: public Subject {
public:
    Model() :
            value(0) {
    }
    Model(const T& init) :
            value(init) {
    }
    virtual void set(const T& v) {
        value = v;
        notify();
    }
    virtual const T& get() const {
        return value;
    }
protected:
    T value;
};
// == CallOnwrite<T, C> ==
template<class T, class C>
class CallOnWrite: public Observer {
public:
    typedef void (C::*PF)();
    CallOnWrite(Model<T>& m, C* po, PF pfu) :
            Observer(m), pointerToComponent(po), pointerToUpdateFunction(pfu) {
    }
    const Model<T>& operator*() const {
        return static_cast<const Model<T>&>(*getPointerToSubject());
    }
    const Model<T>* operator->() const {
        return static_cast<const Model<T>*>(getPointerToSubject());
    }
protected:
    virtual void update() {
        (pointerToComponent->*pointerToUpdateFunction)();
    }
private:
    PF pointerToUpdateFunction;
    C* pointerToComponent;
};
// ==== Application that uses the Classic Observer Pattern ====================
// == ConcreteSubjects ==
typedef Model<bool> Pin;
typedef Model<short> Register;
// == ConcreteObservers ==

template<class T>
class DecDisplay {
public:
    DecDisplay(Model<T>& m, const string& n) :
            cow(m, this, &DecDisplay::update), name(n) {
    }
private:
    void update() {
        cout << name << " = " << dec << cow->get() << endl;
    }
    CallOnWrite<T, DecDisplay<T> > cow;
    string name;
};

typedef DecDisplay<bool> PinDisplay;
// == Simulator ==
class Simulator {
public:
    Register pc; // program counter
    Pin pin1;
    void run() {
        for (short i(9); i < 16; ++i) {
            if (i % 5 == 0)
                pin1.set(!pin1.get());
            pc.set(i);
            cout  << "for = " << i << endl;
        }
    }
};
// == User Interface ==
int main() {
    Simulator s;
    {
        PinDisplay d3(s.pin1, "Pin 1");
        s.run();
    }
    s.run();
    return 0;
}

在第一个例子中,d3只在括号之间的范围内。括号覆盖后,它将超出范围,因此不会显示。看看RAII的概念以及构造函数和析构函数的相关概念。

附言:我们喜欢尽量举一个最小的例子,你所拥有的大多数东西都有点吵。

相关文章:
  • 没有找到相关文章