From 344dc1d4f8ce0101b646e45fbba31002841f4d60 Mon Sep 17 00:00:00 2001 From: kleeman Date: Fri, 19 Aug 2022 08:15:59 -0700 Subject: [PATCH] Add utilities for iterables --- include/albatross/src/utils/iter_utils.hpp | 44 ++++++++++++++++++++++ include/albatross/src/utils/traits.hpp | 42 +++++++++++++++++++++ 2 files changed, 86 insertions(+) create mode 100644 include/albatross/src/utils/iter_utils.hpp create mode 100644 include/albatross/src/utils/traits.hpp diff --git a/include/albatross/src/utils/iter_utils.hpp b/include/albatross/src/utils/iter_utils.hpp new file mode 100644 index 00000000..85c5cb15 --- /dev/null +++ b/include/albatross/src/utils/iter_utils.hpp @@ -0,0 +1,44 @@ +/* + * Copyright (C) 2018 Swift Navigation Inc. + * Contact: Swift Navigation + * + * This source is subject to the license found in the file 'LICENSE' which must + * be distributed together with this source. All other rights reserved. + * + * THIS CODE AND INFORMATION IS PROVIDED "AS IS" WITHOUT WARRANTY OF ANY KIND, + * EITHER EXPRESSED OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND/OR FITNESS FOR A PARTICULAR PURPOSE. + */ + +#ifndef ALBATROSS_ITER_UTILS_H +#define ALBATROSS_ITER_UTILS_H + +namespace albatross { + +/* + * Convenience function instead of using the find == end + * method of checking if a value exists in an iterable + */ +template , int> = 0>> +bool found(const Iterable &iterable, const K &key) { + return std::find(iterable.begin(), iterable.end(), key) != iterable.end(); +} + +template , int> = 0>> +void insert_if_not_found(const Iterable &iterable, const K &key) { + if (!found(iterable, key)) { + std::back_inserter(iterable) = key; + } +} + +template , int> = 0> + > +void eliminate(const K &key, Iterable *iterable) { + std::erase(std::remove(iterable->begin(), iterabled->end(), key)); +} + +} // namespace albatross +#endif diff --git a/include/albatross/src/utils/traits.hpp b/include/albatross/src/utils/traits.hpp new file mode 100644 index 00000000..05186edb --- /dev/null +++ b/include/albatross/src/utils/traits.hpp @@ -0,0 +1,42 @@ +/* + * Copyright (C) 2022 Swift Navigation Inc. + * Contact: Swift Navigation + * + * This source is subject to the license found in the file 'LICENSE' which must + * be distributed together with this source. All other rights reserved. + * + * THIS CODE AND INFORMATION IS PROVIDED "AS IS" WITHOUT WARRANTY OF ANY KIND, + * EITHER EXPRESSED OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND/OR FITNESS FOR A PARTICULAR PURPOSE. + */ + +#ifndef ALBATROSS_UTILS_TRAITS_H +#define ALBATROSS_UTILS_TRAITS_H + +namespace albatross { + +namespace detail { +// Taken from here: +// https://stackoverflow.com/questions/13830158/check-if-a-variable-type-is-iterable + using std::begin; + using std::end; + + template + auto is_iterable_impl(int) + -> decltype ( + begin(std::declval()) != end(std::declval()), // begin/end and operator != + void(), // Handle evil operator , + ++std::declval()))&>(), // operator ++ + void(*begin(std::declval())), // operator* + std::true_type{}); + + template + std::false_type is_iterable_impl(...); + +} + +template +using is_iterable = decltype(detail::is_iterable_impl(0)); + +} // namespace albatross +#endif