TrinityCore
Trinity::Containers Namespace Reference

Functions

template<class C >
void RandomResize (C &container, std::size_t requestedSize)
 
template<class C , class Predicate >
void RandomResize (C &container, Predicate &&predicate, std::size_t requestedSize)
 
template<class C >
auto SelectRandomContainerElement (C const &container) -> typename std::add_const< decltype(*std::begin(container))>::type &
 
template<class C >
auto SelectRandomWeightedContainerElement (C const &container, std::vector< double > const &weights) -> decltype(std::begin(container))
 
template<class C , class Fn >
auto SelectRandomWeightedContainerElement (C const &container, Fn weightExtractor) -> decltype(std::begin(container))
 
template<class Iterator >
void RandomShuffle (Iterator begin, Iterator end)
 Reorder the elements of the iterator range randomly. More...
 
template<class C >
void RandomShuffle (C &container)
 Reorder the elements of the container randomly. More...
 
template<class Iterator1 , class Iterator2 >
bool Intersects (Iterator1 first1, Iterator1 last1, Iterator2 first2, Iterator2 last2)
 
template<class Iterator1 , class Iterator2 , class Predicate >
bool Intersects (Iterator1 first1, Iterator1 last1, Iterator2 first2, Iterator2 last2, Predicate &&equalPred)
 
template<class M >
auto MapGetValuePtr (M &map, typename M::key_type const &key) -> decltype(AddressOrSelf(map.find(key) ->second))
 
template<class K , class V , template< class, class, class... > class M, class... Rest>
void MultimapErasePair (M< K, V, Rest... > &multimap, K const &key, V const &value)
 
template<typename Container , typename Predicate >
std::enable_if_t< std::is_move_assignable_v< decltype(*std::declval< Container >).begin())>, void > EraseIf (Container &c, Predicate p)
 
template<typename Container , typename Predicate >
std::enable_if_t<!std::is_move_assignable_v< decltype(*std::declval< Container >).begin())>, void > EraseIf (Container &c, Predicate p)
 
template<typename T >
decltype(auto) EnsureWritableVectorIndex (std::vector< T > &vec, typename std::vector< T >::size_type i)
 
template<typename T >
decltype(auto) EnsureWritableVectorIndex (std::vector< T > &vec, typename std::vector< T >::size_type i, T const &resizeDefault)
 
template<typename Container , typename NeedleContainer , typename ContainsOperator = bool(std::string const&, std::string const&), typename T = void>
auto FuzzyFindIn (Container const &container, NeedleContainer const &needles, ContainsOperator const &contains=StringContainsStringI, int(*bonus)(decltype((*std::begin(std::declval< Container >()))))=nullptr)
 
template<typename iterator >
constexpr Trinity::IteratorPair< iterator > MakeIteratorPair (iterator first, iterator second)
 
template<typename iterator >
constexpr Trinity::IteratorPair< iterator > MakeIteratorPair (std::pair< iterator, iterator > iterators)
 
template<class M >
auto MapEqualRange (M &map, typename M::key_type const &key) -> IteratorPair< decltype(map.begin())>
 

Function Documentation

◆ EnsureWritableVectorIndex() [1/2]

template<typename T >
decltype(auto) Trinity::Containers::EnsureWritableVectorIndex ( std::vector< T > &  vec,
typename std::vector< T >::size_type  i 
)
inline

Returns a mutable reference to element at index i Will resize vector if neccessary to ensure element at i can be safely written

This exists as separate overload instead of one function with default argument to allow using with vectors of non-default-constructible classes

315  {
316  if (i >= vec.size())
317  vec.resize(i + 1);
318 
319  return vec[i];
320  }
+ Here is the caller graph for this function:

◆ EnsureWritableVectorIndex() [2/2]

template<typename T >
decltype(auto) Trinity::Containers::EnsureWritableVectorIndex ( std::vector< T > &  vec,
typename std::vector< T >::size_type  i,
T const &  resizeDefault 
)
inline

Returns a mutable reference to element at index i Will resize vector if neccessary to ensure element at i can be safely written

This overload allows specifying what value to pad vector with during .resize

330  {
331  if (i >= vec.size())
332  vec.resize(i + 1, resizeDefault);
333 
334  return vec[i];
335  }

◆ EraseIf() [1/2]

template<typename Container , typename Predicate >
std::enable_if_t<std::is_move_assignable_v<decltype(*std::declval<Container>).begin())>, void> Trinity::Containers::EraseIf ( Container &  c,
Predicate  p 
)
280  {
281  auto wpos = c.begin();
282  for (auto rpos = c.begin(), end = c.end(); rpos != end; ++rpos)
283  {
284  if (!p(*rpos))
285  {
286  if (rpos != wpos)
287  std::swap(*rpos, *wpos);
288  ++wpos;
289  }
290  }
291  c.erase(wpos, c.end());
292  }
+ Here is the caller graph for this function:

◆ EraseIf() [2/2]

template<typename Container , typename Predicate >
std::enable_if_t<!std::is_move_assignable_v<decltype(*std::declval<Container>).begin())>, void> Trinity::Containers::EraseIf ( Container &  c,
Predicate  p 
)
296  {
297  for (auto it = c.begin(); it != c.end();)
298  {
299  if (p(*it))
300  it = c.erase(it);
301  else
302  ++it;
303  }
304  }

◆ FuzzyFindIn()

template<typename Container , typename NeedleContainer , typename ContainsOperator = bool(std::string const&, std::string const&), typename T = void>
auto Trinity::Containers::FuzzyFindIn ( Container const &  container,
NeedleContainer const &  needles,
ContainsOperator const &  contains = StringContainsStringI,
int(*)(decltype((*std::begin(std::declval< Container >()))))  bonus = nullptr 
)
31  {
32  using IteratorResult = decltype((*std::begin(container)));
33  using MappedType = std::conditional_t<std::is_reference_v<IteratorResult>, std::reference_wrapper<std::remove_reference_t<IteratorResult>>, IteratorResult>;
34  std::multimap<size_t, MappedType, std::greater<size_t>> results;
35 
36  for (auto outerIt = std::begin(container), outerEnd = std::end(container); outerIt != outerEnd; ++outerIt)
37  {
38  size_t count = 0;
39  for (auto innerIt = std::begin(needles), innerEnd = std::end(needles); innerIt != innerEnd; ++innerIt)
40  if (contains(*outerIt, *innerIt))
41  ++count;
42 
43  if (!count)
44  continue;
45 
46  if (bonus)
47  count += bonus(*outerIt);
48 
49  results.emplace(count, *outerIt);
50  }
51 
52  return results;
53  }

◆ Intersects() [1/2]

template<class Iterator1 , class Iterator2 >
bool Trinity::Containers::Intersects ( Iterator1  first1,
Iterator1  last1,
Iterator2  first2,
Iterator2  last2 
)
inline
210  {
211  while (first1 != last1 && first2 != last2)
212  {
213  if (*first1 < *first2)
214  ++first1;
215  else if (*first2 < *first1)
216  ++first2;
217  else
218  return true;
219  }
220 
221  return false;
222  }
+ Here is the caller graph for this function:

◆ Intersects() [2/2]

template<class Iterator1 , class Iterator2 , class Predicate >
bool Trinity::Containers::Intersects ( Iterator1  first1,
Iterator1  last1,
Iterator2  first2,
Iterator2  last2,
Predicate &&  equalPred 
)
inline
239  {
240  while (first1 != last1 && first2 != last2)
241  {
242  if (*first1 < *first2)
243  ++first1;
244  else if (*first2 < *first1)
245  ++first2;
246  else if (!equalPred(*first1, *first2))
247  ++first1, ++first2;
248  else
249  return true;
250  }
251 
252  return false;
253  }

◆ MakeIteratorPair() [1/2]

template<typename iterator >
constexpr Trinity::IteratorPair<iterator> Trinity::Containers::MakeIteratorPair ( iterator  first,
iterator  second 
)
49  {
50  return { first, second };
51  }
+ Here is the caller graph for this function:

◆ MakeIteratorPair() [2/2]

template<typename iterator >
constexpr Trinity::IteratorPair<iterator> Trinity::Containers::MakeIteratorPair ( std::pair< iterator, iterator >  iterators)
55  {
56  return iterators;
57  }

◆ MapEqualRange()

template<class M >
auto Trinity::Containers::MapEqualRange ( M &  map,
typename M::key_type const &  key 
) -> IteratorPair<decltype(map.begin())>
inline
61  {
62  return { map.equal_range(key) };
63  }
+ Here is the caller graph for this function:

◆ MapGetValuePtr()

template<class M >
auto Trinity::Containers::MapGetValuePtr ( M &  map,
typename M::key_type const &  key 
) -> decltype(AddressOrSelf(map.find(key)->second))
inline

Returns a pointer to mapped value (or the value itself if map stores pointers)

260  {
261  auto itr = map.find(key);
262  return itr != map.end() ? AddressOrSelf(itr->second) : nullptr;
263  }
constexpr T * AddressOrSelf(T &not_ptr)
Definition: Containers.h:39
+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ MultimapErasePair()

template<class K , class V , template< class, class, class... > class M, class... Rest>
void Trinity::Containers::MultimapErasePair ( M< K, V, Rest... > &  multimap,
K const &  key,
V const &  value 
)
inline
267  {
268  auto range = multimap.equal_range(key);
269  for (auto itr = range.first; itr != range.second;)
270  {
271  if (itr->second == value)
272  itr = multimap.erase(itr);
273  else
274  ++itr;
275  }
276  }
+ Here is the caller graph for this function:

◆ RandomResize() [1/2]

template<class C >
void Trinity::Containers::RandomResize ( C &  container,
std::size_t  requestedSize 
)
78  {
79  static_assert(std::is_base_of<std::forward_iterator_tag, typename std::iterator_traits<typename C::iterator>::iterator_category>::value, "Invalid container passed to Trinity::Containers::RandomResize");
80  if (std::size(container) <= requestedSize)
81  return;
82  auto keepIt = std::begin(container), curIt = std::begin(container);
83  uint32 elementsToKeep = requestedSize, elementsToProcess = std::size(container);
84  while (elementsToProcess)
85  {
86  // this element has chance (elementsToKeep / elementsToProcess) of being kept
87  if (urand(1, elementsToProcess) <= elementsToKeep)
88  {
89  if (keepIt != curIt)
90  *keepIt = std::move(*curIt);
91  ++keepIt;
92  --elementsToKeep;
93  }
94  ++curIt;
95  --elementsToProcess;
96  }
97  container.erase(keepIt, std::end(container));
98  }
uint32_t uint32
Definition: Define.h:143
uint32 urand(uint32 min, uint32 max)
Definition: Random.cpp:42
+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ RandomResize() [2/2]

template<class C , class Predicate >
void Trinity::Containers::RandomResize ( C &  container,
Predicate &&  predicate,
std::size_t  requestedSize 
)

First use predicate filter

102  {
104  C containerCopy;
105  std::copy_if(std::begin(container), std::end(container), std::inserter(containerCopy, std::end(containerCopy)), predicate);
106 
107  if (requestedSize)
108  RandomResize(containerCopy, requestedSize);
109 
110  container = std::move(containerCopy);
111  }
void RandomResize(C &container, Predicate &&predicate, std::size_t requestedSize)
Definition: Containers.h:101

◆ RandomShuffle() [1/2]

template<class Iterator >
void Trinity::Containers::RandomShuffle ( Iterator  begin,
Iterator  end 
)
inline

Reorder the elements of the iterator range randomly.

Parameters
beginBeginning of the range to reorder
endEnd of the range to reorder
179  {
180  std::shuffle(begin, end, RandomEngine::Instance());
181  }
static RandomEngine & Instance()
Definition: Random.cpp:93
+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ RandomShuffle() [2/2]

template<class C >
void Trinity::Containers::RandomShuffle ( C &  container)
inline

Reorder the elements of the container randomly.

Parameters
containerContainer to reorder
192  {
193  RandomShuffle(std::begin(container), std::end(container));
194  }
void RandomShuffle(C &container)
Reorder the elements of the container randomly.
Definition: Containers.h:191

◆ SelectRandomContainerElement()

template<class C >
auto Trinity::Containers::SelectRandomContainerElement ( C const &  container) -> typename std::add_const<decltype(*std::begin(container))>::type&
inline
120  {
121  auto it = std::begin(container);
122  std::advance(it, urand(0, uint32(std::size(container)) - 1));
123  return *it;
124  }
uint32_t uint32
Definition: Define.h:143
uint32 urand(uint32 min, uint32 max)
Definition: Random.cpp:42
+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ SelectRandomWeightedContainerElement() [1/2]

template<class C >
auto Trinity::Containers::SelectRandomWeightedContainerElement ( C const &  container,
std::vector< double > const &  weights 
) -> decltype(std::begin(container))
inline
137  {
138  auto it = std::begin(container);
139  std::advance(it, urandweighted(weights.size(), weights.data()));
140  return it;
141  }
uint32 urandweighted(size_t count, double const *chances)
Definition: Random.cpp:87
+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ SelectRandomWeightedContainerElement() [2/2]

template<class C , class Fn >
auto Trinity::Containers::SelectRandomWeightedContainerElement ( C const &  container,
Fn  weightExtractor 
) -> decltype(std::begin(container))
inline
153  {
154  std::vector<double> weights;
155  weights.reserve(std::size(container));
156  double weightSum = 0.0;
157  for (auto& val : container)
158  {
159  double weight = weightExtractor(val);
160  weights.push_back(weight);
161  weightSum += weight;
162  }
163  if (weightSum <= 0.0)
164  weights.assign(std::size(container), 1.0);
165 
166  return SelectRandomWeightedContainerElement(container, weights);
167  }
auto SelectRandomWeightedContainerElement(C const &container, Fn weightExtractor) -> decltype(std::begin(container))
Definition: Containers.h:152