// This file is part of the uSTL library, an STL implementation. // // Copyright (c) 2005 by Mike Sharov // This file is free software, distributed under the MIT License. #pragma once namespace ustl { /// Returns the sum of all elements in [first, last) added to \p init. /// \ingroup NumericAlgorithms /// template inline T accumulate (InputIterator first, InputIterator last, T init) { while (first < last) init += *first++; return (init); } /// Returns the sum of all elements in [first, last) via \p op, added to \p init. /// \ingroup NumericAlgorithms /// template inline T accumulate (InputIterator first, InputIterator last, T init, BinaryFunction binary_op) { while (first < last) init = binary_op (init, *first++); return (init); } /// Assigns range [value, value + (last - first)) to [first, last) /// \ingroup NumericAlgorithms /// template inline void iota (ForwardIterator first, ForwardIterator last, T value) { while (first < last) *first++ = value++; } /// Returns the sum of products of respective elements in the given ranges. /// \ingroup NumericAlgorithms /// template inline T inner_product (InputIterator1 first1, InputIterator1 last1, InputIterator2 first2, T init) { while (first1 < last1) init += *first1++ * *first2++; return (init); } /// Returns the sum of products of respective elements in the given ranges. /// \ingroup NumericAlgorithms /// template inline T inner_product (InputIterator1 first1, InputIterator1 last1, InputIterator2 first2, T init, BinaryOperation1 sumOp, BinaryOperation2 productOp) { while (first1 < last1) init = sumOp (init, productOp (*first1++, *first2++)); return (init); } /// Writes result such that result[i] = sum (first...first+i) /// \ingroup NumericAlgorithms /// template inline OutputIterator partial_sum (InputIterator first, InputIterator last, OutputIterator result) { if (first < last) *result = *first++; while (first < last) *++result = *first++ + *result; return (result); } /// Writes result such that result[i] = sumOp (first...first+i) /// \ingroup NumericAlgorithms /// template inline OutputIterator partial_sum (InputIterator first, InputIterator last, OutputIterator result, BinaryOperation sumOp) { if (first < last) *result = *first++; while (first < last) *++result = sumOp (*first++, *result); return (result); } /// Writes result such that result[i] = first[i] - first[i - 1] /// \ingroup NumericAlgorithms /// template inline OutputIterator adjacent_difference (InputIterator first, InputIterator last, OutputIterator result) { if (first < last) *result++ = *first++; while (first < last) *result++ = *first - *(first - 1); return (result); } /// Writes result such that result[i] = differenceOp (first[i], first[i - 1]) /// \ingroup NumericAlgorithms /// template inline OutputIterator adjacent_difference (InputIterator first, InputIterator last, OutputIterator result, BinaryOperation differenceOp) { if (first < last) *result++ = *first++; while (first < last) *result++ = differenceOp (*first, *(first - 1)); return (result); } /// \brief Returns x^n. /// Donald Knuth's Russian Peasant algorithm. /// \ingroup NumericAlgorithms /// template inline T power (T x, unsigned n) { T result (n % 2 ? x : 1); while (n /= 2) { x *= x; if (n % 2) result *= x; } return (result); } /// \brief Returns x^n, using \p op instead of multiplication. /// Donald Knuth's Russian Peasant algorithm. /// \ingroup NumericAlgorithms /// template inline T power (T x, unsigned n, BinaryOperation op) { T result (n % 2 ? x : 1); while (n /= 2) { x = op (x, x); if (n % 2) result = op (result, x); } return (result); } } // namespace ustl