1#ifndef TATAMI_CHUNKED_ORACULAR_VARIABLE_SLAB_CACHE_HPP
2#define TATAMI_CHUNKED_ORACULAR_VARIABLE_SLAB_CACHE_HPP
4#include <unordered_map>
42template<
typename Id_,
typename Index_,
class Slab_,
typename Size_>
45 std::shared_ptr<const tatami::Oracle<Index_> > my_oracle;
47 size_t my_counter = 0;
49 Index_ my_last_slab_id = 0;
50 size_t my_last_slab_num = -1;
52 Size_ my_max_size, my_used_size = 0;
53 std::vector<Slab_> my_all_slabs;
58 std::unordered_map<Id_, size_t> my_current_cache, my_future_cache;
59 std::vector<std::pair<Id_, size_t> > my_to_populate, my_to_reuse;
60 std::vector<Id_> my_in_need;
61 std::vector<size_t> my_free_pool;
62 size_t my_refresh_point = 0;
72 my_total(my_oracle->total()),
108 return my_oracle->get(my_counter++);
156 template<
class Ifunction_,
class Ufunction_,
class Afunction_,
class Cfunction_,
class Pfunction_>
160 if (
slab_info.first == my_last_slab_id && my_last_slab_num !=
static_cast<size_t>(-1)) {
161 return std::make_pair(my_all_slabs.data() + my_last_slab_num,
slab_info.second);
166 if (my_counter - 1 == my_refresh_point) {
174 while (++my_refresh_point < my_total) {
182 if (my_future_cache.find(
future_slab_info.first) != my_future_cache.end()) {
187 if (
ccIt != my_current_cache.end()) {
196 my_current_cache.erase(
ccIt);
207 auto cIt = my_current_cache.begin();
208 for (
auto a : my_in_need) {
209 if (
cIt != my_current_cache.end()) {
211 my_to_populate.emplace_back(
a,
slab_num);
215 size_t slab_num = my_all_slabs.size();
216 my_all_slabs.push_back(create());
217 my_to_populate.emplace_back(
a,
slab_num);
223 for (;
cIt != my_current_cache.end(); ++
cIt) {
224 my_free_pool.emplace_back(
cIt->second);
227 populate(my_to_populate, my_to_reuse, my_all_slabs);
228 my_to_populate.clear();
231 my_current_cache.clear();
232 my_current_cache.swap(my_future_cache);
237 my_last_slab_num =
ccIt->second;
238 return std::make_pair(my_all_slabs.data() + my_last_slab_num,
slab_info.second);
243 if (!my_free_pool.empty()) {
244 auto slab_num = my_free_pool.back();
246 my_free_pool.pop_back();
249 my_future_cache[slab_id] = 0;
250 my_in_need.push_back(slab_id);
275 return my_current_cache.size();
Oracle-aware cache for variable-size slabs.
Definition OracularVariableSlabCache.hpp:43
OracularVariableSlabCache(std::shared_ptr< const tatami::Oracle< Index_ > > oracle, size_t max_size)
Definition OracularVariableSlabCache.hpp:70
size_t get_num_slabs() const
Definition OracularVariableSlabCache.hpp:274
size_t get_used_size() const
Definition OracularVariableSlabCache.hpp:267
std::pair< const Slab_ *, Index_ > next(Ifunction_ identify, Ufunction_ upper_size, Afunction_ actual_size, Cfunction_ create, Pfunction_ populate)
Definition OracularVariableSlabCache.hpp:157
OracularVariableSlabCache(const OracularVariableSlabCache &)=delete
OracularVariableSlabCache & operator=(const OracularVariableSlabCache &)=delete
size_t get_max_size() const
Definition OracularVariableSlabCache.hpp:259
Index_ next()
Definition OracularVariableSlabCache.hpp:107
Methods to handle chunked tatami matrices.
Definition ChunkDimensionStats.hpp:4
Statistics for regular chunks along a dimension.
Definition ChunkDimensionStats.hpp:35