From fdd072770cdcef4727b35917674980eea5f22748 Mon Sep 17 00:00:00 2001 From: Metehan Tuncbilek Date: Fri, 20 Sep 2024 18:03:13 +0300 Subject: [PATCH] initial version. --- .../Data/Containers/BinSearchArrayMap.hpp | 106 ++++++++++++++++++ tests/BinSearchArrayMapTest.cpp | 42 +++++++ 2 files changed, 148 insertions(+) create mode 100644 openVulkanoCpp/Data/Containers/BinSearchArrayMap.hpp create mode 100644 tests/BinSearchArrayMapTest.cpp diff --git a/openVulkanoCpp/Data/Containers/BinSearchArrayMap.hpp b/openVulkanoCpp/Data/Containers/BinSearchArrayMap.hpp new file mode 100644 index 0000000..ee14317 --- /dev/null +++ b/openVulkanoCpp/Data/Containers/BinSearchArrayMap.hpp @@ -0,0 +1,106 @@ +/* +* This Source Code Form is subject to the terms of the Mozilla Public +* License, v. 2.0. If a copy of the MPL was not distributed with this +* file, You can obtain one at https://mozilla.org/MPL/2.0/. +*/ + +#pragma once + +#include +#include +#include +#include + +namespace OpenVulkano +{ + template, typename Vec = std::vector, + typename = std::enable_if_t::value>> + class BinSearchArrayMap + { + public: + BinSearchArrayMap() = default; + ~BinSearchArrayMap() = default; + + void Insert(K key, V value) noexcept + { + // Check if the key is bigger than the last element + if (m_data.empty() || key > m_data.back().first) + { + m_data.emplace_back(key, value); + return; + } + + throw std::runtime_error("Key cannot be lesser than the last used key."); + } + + template void Emplace(K key, Args... args) + { + // Check if the key is bigger than the last element + if (m_data.empty() || key > m_data.back().first) + { + m_data.emplace_back(key, V(args...)); + return; + } + + throw std::runtime_error("Key cannot be lesser than the last used key."); + } + + void Remove(K key) noexcept + { + auto it = std::lower_bound(m_data.begin(), m_data.end(), key, + [](const auto& pair, const K& key) { return pair.first < key; }); + + if (it != m_data.end()) + { + m_data.erase(it); + } + else + { + throw std::runtime_error("Key not found."); + } + } + + void Size() const noexcept { m_data.size(); } + + V& operator[](K key) noexcept + { + auto it = std::lower_bound(m_data.begin(), m_data.end(), key, + [](const auto& pair, const K& key) { return pair.first < key; }); + + return it->second; + } + + V& Get(K key) noexcept { + auto it = std::lower_bound(m_data.begin(), m_data.end(), key, + [](const auto& pair, const K& key) { return pair.first < key; }); + + if (it != m_data.end()) + { + return it->second; + } + else + { + throw std::runtime_error("Key not found."); + } + } + + bool Contains(K key) const noexcept + { + auto it = std::lower_bound(m_data.begin(), m_data.end(), key, + [](const auto& pair, const K& key) { return pair.first < key; }); + + return it != m_data.end(); + } + + bool Contains(V& value) const noexcept + { + auto it = + std::find_if(m_data.begin(), m_data.end(), [&value](const auto& pair) { return pair.second == value; }); + + return it != m_data.end(); + } + + private: + Vec m_data; + }; +} diff --git a/tests/BinSearchArrayMapTest.cpp b/tests/BinSearchArrayMapTest.cpp new file mode 100644 index 0000000..ea5e4e5 --- /dev/null +++ b/tests/BinSearchArrayMapTest.cpp @@ -0,0 +1,42 @@ +/* +* This Source Code Form is subject to the terms of the Mozilla Public +* License, v. 2.0. If a copy of the MPL was not distributed with this +* file, You can obtain one at https://mozilla.org/MPL/2.0/. +*/ + +#include + +#include +#include +#include +#include + +#include "Data/Containers/BinSearchArrayMap.hpp" + +using namespace OpenVulkano; + +TEST_CASE("BinSearchArrayMap") +{ + std::vector> data; + data.push_back(std::make_pair(1, "One")); + data.push_back(std::make_pair(2, "Two")); + data.push_back(std::make_pair(6, "Three")); + data.push_back(std::make_pair(8, "Four")); + data.push_back(std::make_pair(10, "Five")); + + auto wtf = + std::lower_bound(data.begin(), data.end(), 10, [](const auto& pair, const int& key) { return pair.first < key; }); + + auto test = *wtf; + REQUIRE(test.first == 10); + REQUIRE(test.second == "Five"); + + BinSearchArrayMap map; + map.Insert(1, "One"); + map.Insert(2, "Two"); + map.Insert(6, "Three"); + map.Insert(8, "Four"); + map.Insert(10, "Five"); + + REQUIRE(map[6] == "Three"); +}