В духе публикации заметок на разных языках я хотел бы ответить на @ onebyone.livejournal.com примером C ++ без изменения языка.
Во-первых, памятка для функций с одним аргументом:
template <class Result, class Arg, class ResultStore = std::map<Arg, Result> >
class memoizer1{
public:
template <class F>
const Result& operator()(F f, const Arg& a){
typename ResultStore::const_iterator it = memo_.find(a);
if(it == memo_.end()) {
it = memo_.insert(make_pair(a, f(a))).first;
}
return it->second;
}
private:
ResultStore memo_;
};
Просто создайте экземпляр памятки, передайте ему свою функцию и аргумент. Просто убедитесь, что вы не разделяете одну и ту же заметку между двумя разными функциями (но вы можете поделиться ею между разными реализациями одной и той же функции).
Далее, функция драйвера и реализация. только функция драйвера должна быть общедоступной
int fib (int); // Водитель
int fib_ (int); // реализация
Реализован:
int fib_(int n){
++total_ops;
if(n == 0 || n == 1)
return 1;
else
return fib(n-1) + fib(n-2);
}
И драйвер, чтобы запомнить
int fib(int n) {
static memoizer1<int,int> memo;
return memo(fib_, n);
}
Постоянная ссылка, показывающая вывод на codepad.org. Количество звонков измеряется для проверки правильности. (введите юнит-тест здесь ...)
Это запоминает только одну функцию ввода. Обобщение для нескольких аргументов или различных аргументов оставлено в качестве упражнения для читателя.