缓存的getter/calculations模式|具有依赖项跟踪的boost类
cached getter/calculations pattern|boost class with dependency tracking
对于"缓存计算"/"缓存getter",是否有通用模式或准备使用boost类?
我的意思是:
class Test{
public:
Value getValue() const;
protected:
Value calculateValue() const;//REALLY expensive operation.
mutable bool valueIsDirty;
mutable Value cachedValue;
}
Value Test::getValue() const{
if (valueIsDirty){
cachedValue = calculateValue();
valueIsDirty = false;
}
return cachedValue;
}
我可以使用std::pair<Value, bool>
并将getValue/calculateValue
转换为宏,但如果值依赖于其他值(存储在其他类中),并且这些值也可以缓存,则这并没有真正的帮助。
对于这种"模式",有现成的解决方案吗?目前,我手动处理这样的缓存值,但这并不"好看"。
限制:
c++03标准。允许Boost。
Proxy设计模式可以帮助实现这一点。
一个典型的实现将定义一个类ValuePtr
,它的行为与普通的Value*
一样,即它有一个过载的operator->
和operator*
。但是,这些运算符并不直接访问底层Value
对象,而是包含决定加载或重新计算实际值的逻辑。这种额外的间接级别将封装代理逻辑。
如果您需要计算对其他对象的引用,也许std::shared_ptr<Value>
可以用作ValuePtr
中的underyling数据类型。
有关代码示例,请参阅此网站。提升。Flyweight也可能有所帮助。
这就是我最终使用的:
template<typename T, typename Owner> class CachedMemberValue{
public:
typedef T (Owner::*Callback)() const;
T get(){
if (dirty){
cachedValue = (owner->*calculateCallback)();
dirty = false;
}
return cachedValue;
}
const T& getRef(){
if (dirty){
cachedValue = (owner->*calculateCallback)();
dirty = false;
}
return cachedValue;
}
void markDirty(){
dirty = true;
}
CachedMemberValue(Owner* owner_, Callback calculateCallback_)
:owner(owner_), calculateCallback(calculateCallback_), dirty(true){
}
protected:
Owner *owner;
Callback calculateCallback;
bool dirty;
T cachedValue;
private:
CachedMemberValue(const CachedMemberValue<T, Owner>&){
}
CachedMemberValue<T, Owner>& operator=(const CachedMemberValue<T, Owner>&){
return *this;
}
};
用法:
class MyClass{
public:
int getMin() const{
return cachedMin.get();
}
void modifyValue() { /*... calculation/modification*/ cachedMin.markDirty();}
MyClass(): cachedMin(this, &MyClass::noncachedGetMin){}
private:
int noncachedGetMin() const{ /*expensive operation here*/ ... }
mutable CachedMemberValue<int, MyClass> cachedMin;
};
相关文章:
- 如何从C++中的依赖类型中获得它所依赖的类型
- 将--whole archive链接器选项与CMake和具有其他库依赖项的库一起使用
- 光线跟踪器灯光反射错误
- 将依赖名称显式标记为类型名和模板的奇怪之处
- 人脸跟踪arduino代码的优化
- 在 Windows 上,是否可以让 dll 在不使用 PATH 环境变量的情况下在另一个文件夹中查找依赖项?
- C++GTKMM gui循环依赖关系
- 通过ccmake在cmake中缓存依赖选项
- 跟踪滚动条上的鼠标事件
- 当基类是依赖类型时,这是一个缺陷吗
- 如何使用新运算符跟踪在循环中创建的 QLabel
- 从不同的附加依赖项中识别等同命名的函数
- 如何在 CMake 中对目标依赖项进行分组?
- 是否可以依赖函数范围的静态变量来执行程序关闭期间调用的方法?
- 为什么构建目录中新构建的共享库与安装目录中的副本具有不同的依赖项集?
- CMake 标头依赖项跟踪似乎不适用于target_include_directories?
- 缓存的getter/calculations模式|具有依赖项跟踪的boost类
- 为什么依赖跟踪器显示丢失的dll
- 跟踪哪个依赖项包含 SSE 指令
- GCC依赖跟踪:-M比-MM好吗?