Welcome to mirror list, hosted at ThFree Co, Russian Federation.

github.com/moses-smt/nplm.git - Unnamed repository; edit this file 'description' to name the repository.
summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
Diffstat (limited to 'src/find_string.hpp')
-rw-r--r--src/find_string.hpp77
1 files changed, 77 insertions, 0 deletions
diff --git a/src/find_string.hpp b/src/find_string.hpp
new file mode 100644
index 0000000..fd612fd
--- /dev/null
+++ b/src/find_string.hpp
@@ -0,0 +1,77 @@
+/** \file \author Jonathan Graehl <graehl@gmail.com>
+
+ find_string(boost::unordered_map<std::string, ...>, pair<char const*, char
+ const*>) pair is [begin, end), a key: map.find(std:string(key.first,
+ key.second)) read-only since unordered_map doesn't support lazy construction
+ of string from a pair key.
+
+ To the extent possible under law, the author(s) have dedicated all copyright
+ and related and neighboring rights to this software to the public domain
+ worldwide. This software is distributed without any warranty.
+*/
+
+#ifndef FIND_STRING_GRAEHL_2015_06_24_HPP
+#define FIND_STRING_GRAEHL_2015_06_24_HPP
+#pragma once
+
+#include <utility>
+#include <algorithm>
+#include <cstddef>
+#include <boost/functional/hash.hpp>
+
+namespace std {
+/// we do not change standard semantics of any supported comparison e.g. pair vs
+/// pair, but simply allow string to be compared against pair of char pointers.
+inline bool operator==(std::string const& str, std::pair<char const*, char const*> slice) {
+ return str.size() == (slice.second - slice.first) && std::equal(slice.first, slice.second, str.begin());
+}
+inline bool operator==(std::pair<char const*, char const*> slice, std::string const& str) {
+ return str.size() == (slice.second - slice.first) && std::equal(slice.first, slice.second, str.begin());
+}
+inline bool operator==(std::string const& str, std::pair<char*, char*> slice) {
+ return str.size() == (slice.second - slice.first) && std::equal(slice.first, slice.second, str.begin());
+}
+inline bool operator==(std::pair<char*, char*> slice, std::string const& str) {
+ return str.size() == (slice.second - slice.first) && std::equal(slice.first, slice.second, str.begin());
+}
+/// techinically not allowed but easiest route to ADL. we could rename these instead.
+inline std::size_t hash_value(std::pair<char const*, char const*> slice) {
+ return boost::hash_range(slice.first, slice.second);
+}
+inline std::size_t hash_value(std::pair<char*, char*> slice) {
+ return boost::hash_range(slice.first, slice.second);
+}
+inline std::size_t hash_value(std::string const& str) {
+ return boost::hash_range(str.begin(), str.end());
+}
+}
+
+struct slice_or_string_eq {
+ typedef bool result_type;
+ template <class A, class B>
+ bool operator()(A const& a, B const& b) const {
+ return a == b;
+ }
+};
+
+struct slice_or_string_hash {
+ typedef std::size_t result_type;
+ template <class Slice>
+ std::size_t operator()(Slice const& slice) const {
+ return hash_value(slice);
+ }
+};
+
+/// \return map.find(std:string(key.first, key.second)) but faster
+template <class UnorderedMap, class Slice>
+typename UnorderedMap::const_iterator find_string(UnorderedMap const& map, Slice const& key) {
+ return map.find(key, slice_or_string_hash(), slice_or_string_eq());
+}
+
+/// \return map.find(std:string(key.first, key.second)) but faster
+template <class UnorderedMap, class Slice>
+typename UnorderedMap::iterator find_string(UnorderedMap& map, Slice const& key) {
+ return map.find(key, slice_or_string_hash(), slice_or_string_eq());
+}
+
+#endif