Mitsuba Renderer  0.5.0
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros Groups Pages
simplecache.h
Go to the documentation of this file.
1 /*
2  This file is part of Mitsuba, a physically based rendering system.
3 
4  Copyright (c) 2007-2014 by Wenzel Jakob and others.
5 
6  Mitsuba is free software; you can redistribute it and/or modify
7  it under the terms of the GNU General Public License Version 3
8  as published by the Free Software Foundation.
9 
10  Mitsuba is distributed in the hope that it will be useful,
11  but WITHOUT ANY WARRANTY; without even the implied warranty of
12  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13  GNU General Public License for more details.
14 
15  You should have received a copy of the GNU General Public License
16  along with this program. If not, see <http://www.gnu.org/licenses/>.
17 */
18 
19 #pragma once
20 #if !defined(__MITSUBA_CORE_CACHE_H_)
21 #define __MITSUBA_CORE_CACHE_H_
22 
23 #include <mitsuba/core/tls.h>
24 
26 
27 /**
28  * \brief Generic thread-local storage for caching evaluations of
29  * expensive function calls
30  *
31  * This class implements a simple and efficient one-entry storage for caching
32  * the result of a call to an expensive-to-evaluate function that has no side
33  * effects.
34  *
35  * The target application is a situation where multiple threads are causing
36  * calls to such a function and each individual thread may invoke it a few
37  * times in a row using the same input argument.
38  *
39  * This storage class provides the means to avoid re-evaluating the function
40  * in this case. By isolating threads from one another, it does not suffer
41  * heavy costs for inter-thread synchronizations.
42  *
43  * Here is an example snippet:
44  *
45  * \code
46  * struct MyFunctor {
47  * inline void operator()(const Point &input, Float &output) {
48  * // .... Perform expensive function call / computation .....
49  * }
50  * };
51  *
52  * void test() {
53  * SimpleCache<Point, Float> myCache;
54  * MyFunctor functor;
55  *
56  * // First call -- evaluate the functor for the given input
57  * Float result = myCache.get(functor, Point(1,2,3));
58  *
59  * // Now, the evaluation can uses the cached value
60  * Float result2 = myCache.get(functor, Point(1,2,3));
61  * }
62  *
63  * \endcode
64  *
65  * \tparam ArgType
66  * Argument type of the function whose return values should be cached
67  *
68  * \tparam ReturnType
69  * Return type of the function whose return values should be cached
70  */
71 template <typename ArgType, typename ReturnType> class SimpleCache
72  : protected PrimitiveThreadLocal< std::pair<ArgType, ReturnType> > {
73 protected:
74  typedef std::pair<ArgType, ReturnType> ValueType;
76 public:
78 
79  /**
80  * \brief Return the cache entry for the argument \c argument
81  * or run \c UpdateFunctor to compute it
82  */
83  template <typename UpdateFunctor> inline ReturnType &get(const UpdateFunctor &functor, const ArgType &argument) {
84  bool existed;
85  ValueType *value = (ValueType *) this->m_base.get(existed);
86 
87  if (EXPECT_NOT_TAKEN(!existed || value->first != argument)) {
88  value->first = argument;
89  functor(value->first, value->second);
90  }
91 
92  return value->second;
93  }
94 };
95 
97 
98 #endif /* __MITSUBA_CORE_CACHE_H_ */
ValueType & get()
Return a reference to the data associated with the current thread.
Definition: tls.h:127
std::pair< ArgType, ReturnType > ValueType
Definition: simplecache.h:74
#define MTS_NAMESPACE_BEGIN
Definition: platform.h:137
SimpleCache()
Definition: simplecache.h:77
PrimitiveThreadLocal< ValueType > ParentType
Definition: simplecache.h:75
Thin wrapper around posix thread local storage. Stores heap-allocated data other than Object instance...
Definition: tls.h:115
#define MTS_NAMESPACE_END
Definition: platform.h:138
Generic thread-local storage for caching evaluations of expensive function calls. ...
Definition: simplecache.h:71