BLAM-Lab-Projects / experiment-code

Note: As of June 2017, AW is no longer supporting this version of the code. Recommended switching over to the SDL2 repository.
0 stars 0 forks source link

Shifting experiment-specific code out of main #10

Open aforren1 opened 8 years ago

aforren1 commented 8 years ago

This thought isn't fully formed yet (and the syntax is probably very off), but I just wanted to start writing it down. A more realistic (but MATLAB) example can be found on my state_machine branch (see matlab/Experiments and main2.m).

(See https://en.wikibooks.org/wiki/C%2B%2B_Programming/Code/Design_Patterns#Factory for better run-through of the factory design pattern)

// abstract class
class Experiment {
    public:    
        virtual void Experiment() = 0; // pure virtual methods *must* be implemented
        virtual ~Experiment() {}
        std::string GetState() { return state; }

    private:
        std::string state = "";
};

// derived class
class TimedResponse: public Experiment {
    public:
        void TimedResponse() override { state = "idle"; };
        void SetPeriod(int new_period) { beep_period = new_period; };
        virtual ~TimedResponse() {};

    private:
        int beep_period = 800; // in milliseconds
};

// factory class (makes the above derived class)
class ExperimentFactory {
public:
    static Experiment *NewExperiment(const std::string &exp_type)
    {
        if(exp_type == "timedresponse")
            return new TimedResponse;
        // additional statements here for additional derived classes (experiments)
        // This would be the only file that is necessary to update
        return NULL;
    }
};

// example main
int main(int argc, char *argv[]) {

    if (argc != 2) {
        printf("One argument only!");
        abort();
    }

    ExperimentFactory* factory = new ExperimentFactory();
    // the string arg to NewExperiment can be set at runtime
    Experiment experiment = factory->NewExperiment(argv[1]);

    while(GetState(experiment) != "finished") {
        // do things
    }
}

Calling the executable with a single argument (eg. experiment.exe "timedresponse") ought to give the correct object.

One advantage of this is that only the file with the ExperimentFactory needs to be modified when experiments are added.