File utils.hxx#

A mix of short utilities for memory management, strings, and some simple but common calculations

Copyright 2010 - 2025 BOUT++ contributors

Contact: Ben Dudson, dudson2@llnl.gov

This file is part of BOUT++.

BOUT++ is free software: you can redistribute it and/or modify it under the terms of the GNU Lesser General Public License as published by the Free Software Foundation, either version 3 of the License, or (at your option) any later version.

BOUT++ is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License for more details.

You should have received a copy of the GNU Lesser General Public License along with BOUT++. If not, see http://www.gnu.org/licenses/.

Defines

BOUT_CONCAT_(A, B)#

Utility to evaluate and concatenate macro symbols Note that ## operator doesn’t evaluate symols A or B

BOUT_CONCAT(A, B)#

Functions

template<typename T>
bool operator==(const Matrix<T> &lhs, const Matrix<T> &rhs)#
template<typename T>
bool operator==(const Tensor<T> &lhs, const Tensor<T> &rhs)#
inline BoutReal randomu()#

Get Random number between 0 and 1

template<typename T>
inline T SQ(const T &t)#

Calculate the square of a variable t i.e. t * t

template<> inline BOUT_HOST_DEVICE BoutReal SQ (const BoutReal &t)
inline int ROUND(BoutReal x)#

Round x to the nearest integer

template<typename T>
T BOUTMAX(T a)#

Calculate the maximum of a list of values using a > b operator

template<typename T, typename ...Args>
T BOUTMAX(T a, T b, Args... args)#
template<typename T>
T BOUTMIN(T a)#

Calculate the minimum of a list of values using the a < b operator

template<typename T, typename ...Args>
T BOUTMIN(T a, T b, Args... args)#
inline bool is_pow2(int x)#

Check if a number is a power of 2

template<typename T>
T SIGN(T a)#

Return the sign of a number a by testing if a > 0

inline BoutReal MINMOD(BoutReal a, BoutReal b)#

The minimum absolute value of a and b

if a and b have opposite signs, return zero

if |a| < |b| then return a, otherwise return b

inline void checkData(BoutReal f)#

Throw an exception if f is not finite.

char *copy_string(const char *s)

Allocate memory and copy string s

template<class T>
std::string toString(const T &val)#

Convert a value to a string by writing to a stringstream

inline std::string toString(const std::string &val)#

Simple case where input is already a string This is so that toString can be used in templates where the type may be std::string.

template<typename T>
inline std::string toString(const Array<T> &val)#
template<typename T>
inline std::string toString(const Matrix<T> &val)#
template<typename T>
inline std::string toString(const Tensor<T> &val)#
inline std::string toString(const bool &val)#

Convert a bool to “true” or “false”.

inline std::string toString(const DirectionTypes &dir)#
std::string toString(const time_t &time)

Convert a time stamp to a string This uses std::localtime and std::put_time

const std::string lowercase(const std::string &str)

Convert a string to lower case

const std::string uppercase(const std::string &str)

Convert a string to upper case

const std::string lowercasequote(const std::string &str)

Convert to lower case, except inside quotes (” or ‘)

BoutReal stringToReal(const std::string &s)

Convert a string to a BoutReal Throws BoutException if can’t be done

int stringToInt(const std::string &s)

Convert a string to an int

Throws BoutException if can’t be done

std::list<std::string> &strsplit(const std::string &s, char delim, std::list<std::string> &elems)

Split a string on a given delimiter

Parameters:
  • s[in] The string to split (not modified by call)

  • delim[in] The delimiter to split on (single char)

  • elems[inout] A list to which the pieces will be appended using push_back

std::list<std::string> strsplit(const std::string &s, char delim)

Split a string on a given delimiter

Parameters:
  • s[in] The string to split (not modified by call)

  • delim[in] The delimiter to split on (single char)

std::string trim(const std::string &s, const std::string &c = " \t\r")

Strips leading and trailing spaces from a string

Parameters:
  • s[in] The string to trim (not modified)

  • c[in] Collection of characters to remove

std::string trimLeft(const std::string &s, const std::string &c = " \t")

Strips leading spaces from a string

Parameters:
  • s[in] The string to trim (not modified)

  • c[in] Collection of characters to remove

std::string trimRight(const std::string &s, const std::string &c = " \t\r")

Strips leading spaces from a string

Parameters:
  • s[in] The string to trim (not modified)

  • c[in] Collection of characters to remove

std::string trimComments(const std::string &s, const std::string &c = "#;")

Strips the comments from a string

Parameters:
  • s[in] The string to trim (not modified)

  • c[in] Collection of characters to remove

std::string::size_type editDistance(const std::string &str1, const std::string &str2)

Returns the “edit distance” between two strings: how many insertions, deletions, substitutions and transpositions are needed to transform str1 into str2

Implemented using the “optimal string alignment distance” from Wikipedia: https://en.wikipedia.org/wiki/Damerau%E2%80%93Levenshtein_distance#Optimal_string_alignment_distance

template<class T>
std::enable_if<!std::numeric_limits<T>::is_integer, bool>::type almost_equal(T x, T y, int ulp = 2)#
template<typename T>
T *pointer(T *val)#

Convert pointer or reference to pointer This allows consistent handling of both in macros, templates

template<typename T>
T *pointer(T &val)#
template<typename T>
class Matrix#
#include <utils.hxx>

Helper class for 2D arrays

Allows bounds checking through operator() with CHECK > 1

If either n1 or n2 are 0, the Matrix is empty and should not be indexed

Public Types

using data_type = T#
using size_type = int#

Public Functions

Matrix() = default#
Matrix(Matrix&&) noexcept = default#
Matrix &operator=(Matrix&&) noexcept = default#
inline Matrix(size_type n1, size_type n2)#
inline Matrix(const Matrix &other)#
~Matrix() = default#
inline void reallocate(size_type new_size_1, size_type new_size_2)#

Reallocate the Matrix to shape new_size_1 by new_size_2

Note that this invalidates the existing data!

inline Matrix &operator=(const Matrix &other)#
inline T &operator()(size_type i1, size_type i2)#
inline const T &operator()(size_type i1, size_type i2) const#
inline Matrix &operator=(const T &val)#
inline T *begin()#
inline const T *begin() const#
inline T *end()#
inline const T *end() const#
inline std::tuple<size_type, size_type> shape() const#
inline bool empty() const#
inline void ensureUnique()#

Ensures that this Matrix does not share data with another This should be called before performing any write operations on the data.

inline Array<T> &getData()#

Access the underlying storage.

inline const Array<T> &getData() const#

Private Members

size_type n1 = {0}#
size_type n2 = {0}#
Array<T> data#

Underlying 1D storage array.

template<typename T>
class Tensor#
#include <utils.hxx>

Helper class for 3D arrays

Allows bounds checking through operator() with CHECK > 1

If any of n1, n2 or n3 are 0, the Tensor is empty and should not be indexed

Public Types

using data_type = T#
using size_type = int#

Public Functions

Tensor() = default#
Tensor(Tensor&&) noexcept = default#
Tensor &operator=(Tensor&&) noexcept = default#
inline Tensor(size_type n1, size_type n2, size_type n3)#
inline Tensor(const Tensor &other)#
~Tensor() = default#
inline void reallocate(size_type new_size_1, size_type new_size_2, size_type new_size_3)#

Reallocate the Tensor with shape new_size_1 by new_size_2 by new_size_3

Note that this invalidates the existing data!

inline Tensor &operator=(const Tensor &other)#
inline T &operator()(size_type i1, size_type i2, size_type i3)#
inline const T &operator()(size_type i1, size_type i2, size_type i3) const#
inline const T &operator[](Ind3D i) const#
inline T &operator[](Ind3D i)#
inline Tensor &operator=(const T &val)#
inline T *begin()#
inline const T *begin() const#
inline T *end()#
inline const T *end() const#
inline std::tuple<size_type, size_type, size_type> shape() const#
inline bool empty() const#
inline void ensureUnique()#

Ensures that this Tensor does not share data with another This should be called before performing any write operations on the data.

inline Array<T> &getData()#

Access the underlying storage.

inline const Array<T> &getData() const#

Private Members

size_type n1 = {0}#
size_type n2 = {0}#
size_type n3 = {0}#
Array<T> data#

Underlying 1D storage array.

namespace bout

Provides access to the Hypre library, handling initialisation and finalisation.

Usage

#include <bout/hyprelib.hxx>

class MyClass { public:

private: HypreLib lib; };

This will then automatically initialise Hypre the first time an object is created, and finalise it when the last object is destroyed.

Copyright 2012 B.D.Dudson, S.Farley, M.V.Umansky, X.Q.Xu

Contact: Ben Dudson, bd512@york.ac.uk

This file is part of BOUT++.

BOUT++ is free software: you can redistribute it and/or modify it under the terms of the GNU Lesser General Public License as published by the Free Software Foundation, either version 3 of the License, or (at your option) any later version.

BOUT++ is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License for more details.

You should have received a copy of the GNU Lesser General Public License along with BOUT++. If not, see http://www.gnu.org/licenses/.

Explicit inversion of a 3x3 matrix a

If the matrix is singular (ill conditioned), the determinant is return. Otherwise, an empty std::optional is return

SNB model

namespace utils

Functions

template<class T, class ...Args>
_Unique_if<T>::_Single_object make_unique(Args&&... args)#
template<class T>
_Unique_if<T>::_Unknown_bound make_unique(size_t n)#
template<class T, class ...Args>
_Unique_if<T>::_Known_bound make_unique(Args&&...) = delete#
template<class Key, class Compare, class Alloc, class Pred>
std::multiset<Key, Compare, Alloc>::size_type erase_if(std::multiset<Key, Compare, Alloc> &c, Pred pred)#

Erases all elements from c that satisfy the predicate pred from the container. Implementation of C++20’s std::erase_if, taken from https://en.cppreference.com/w/cpp/container/multiset/erase_if CC-BY-SA

template<class Key, class Compare, class Alloc, class Pred>
std::set<Key, Compare, Alloc>::size_type erase_if(std::set<Key, Compare, Alloc> &c, Pred pred)#

Erases all elements from c that satisfy the predicate pred from the container. Implementation of C++20’s std::erase_if, taken from https://en.cppreference.com/w/cpp/container/set/erase_if CC-BY-SA

template<class T, class Alloc, class U>
std::vector<T, Alloc>::size_type erase(std::vector<T, Alloc> &c, const U &value)#

Erases all elements from c that compare equal to value from the container. Implementation of C++20’s std::erase_if, taken from https://en.cppreference.com/w/cpp/container/vector/erase2 CC-BY-SA

template<class T, class Alloc, class Pred>
std::vector<T, Alloc>::size_type erase_if(std::vector<T, Alloc> &c, Pred pred)#

Erases all elements from c that satisfy the predicate pred from the container. Implementation of C++20’s std::erase_if, taken from https://en.cppreference.com/w/cpp/container/vector/erase2 CC-BY-SA

inline bool flagSet(int bitset, int flag)#

Check that flag is set in bitset.

template<class T>
struct _Unique_if#

Public Types

using _Single_object = std::unique_ptr<T>#
template<class T>
struct _Unique_if<T[]>#

Public Types

using _Unknown_bound = std::unique_ptr<T[]>#
template<class T, size_t N>
struct _Unique_if<T[N]>#

Public Types

using _Known_bound = void#
template<typename R, typename ...Args>
struct function_traits<R (*)(Args...)>#
#include <utils.hxx>

Traits class to get the types of function arguments for function pointers

Use like: using some_function = int(*)(int, double, std::string); // Get the type of the first argument: using first_argument_type = bout::utils::function_traits<some_function>::arg<1>::type; // The following prints “true”: std::cout << std::boolalpha << std::is_same_v<double, first_argument_type>;

Adapted from https://stackoverflow.com/a/9065203/2043465

Public Types

using result_type = R#
template<size_t i>
using arg_t = typename arg<i>::type#

Public Static Attributes

static constexpr size_t nargs = sizeof...(Args)#

Total number of arguments.

template<size_t i>
struct arg#

Public Types

using type = typename std::tuple_element<i, std::tuple<Args...>>::type#