関数ポインタを使ったお手軽なStrategyパターン
「Rubyによるデザインパターン」にのってるコードをC++に翻訳中
関数ポインタつかうと、いろいろpublicにしなきゃならんのね
Report.hpp
#include <string> #include <vector> using namespace std; class Report { public: Report (void (*)(Report&)); void output_report (); string title; vector<string> text; private: void (*formatter)(Report&); };
Report.cpp
#include <string> #include <vector> #include "Report.hpp" Report::Report (void (*fn)(Report&)) { title = "月次報告"; text.push_back ("順調"); text.push_back ("最高の調子"); formatter = fn; } void Report::output_report () { (*formatter)(*this); }
stra.cpp
#include "Report.hpp" #include <iostream> #include <string> #include <vector> void plaintextformatter (Report &context) { cout << "*** " + context.title + " ***" << endl; for (vector<string>::iterator line = context.text.begin (); line != context.text.end (); ++line) { cout << *line << endl; } } void htmlformatter (Report &context) { cout << "<html>" << endl; cout << " <head>" << endl; cout << " <title>" + context.title + "</title>" << endl; cout << " </head>" << endl; cout << " <body>" << endl; for (vector<string>::iterator line = context.text.begin (); line != context.text.end (); ++line) { cout << " <p>" + *line + "</p>" << endl; } cout << " </body>" << endl; cout << "</html>" << endl; } int main (int args, char *argv[]) { Report *htmlreport = new Report (htmlformatter); Report *textreport = new Report (plaintextformatter); #ifdef HTML htmlreport->output_report (); #endif /*HTML*/ #ifdef TEXT textreport->output_report (); #endif /*TEXT*/ delete htmlreport; delete textreport; }