// Copyright (C) 2014-2015 ChaosForge Ltd // http://chaosforge.org/ // // This file is part of Nova libraries. // For conditions of distribution and use, see copying.txt file in root folder. /** * @file string_table.hh * @author Kornel Kisielewicz */ #ifndef NV_STL_STRING_TABLE_HH #define NV_STL_STRING_TABLE_HH #include #include #include #include #include namespace nv { class string_table : noncopyable { public: typedef string_view value_type; typedef shash64 key_type; typedef uint64 hash_type; typedef uint32 size_type; typedef uint16 length_type; typedef unordered_map< hash_type, size_type > indexer_type; typedef vector< char > storage_type; typedef indexer_type::const_iterator const_iterator; string_table() {} string_table( stream& in ); void insert( string_table* in ); key_type insert( const value_type& str ) { hash_type hash_value = str.get_hash< uint64 >(); insert( hash_value, str ); return key_type( hash_value ); } bool exists( key_type i ) const { return m_map.find( i.value() ) != m_map.end(); } value_type at( key_type i ) const { const auto& it = m_map.find( i.value() ); NV_ASSERT_ALWAYS( it != m_map.end(), "Key not found in string_table!" ); return extract_raw( it->second ); } value_type operator[]( key_type i ) const { const auto& it = m_map.find( i.value() ); return it != m_map.end() ? extract_raw( it->second ) : value_type(); } uint32 size() const { return m_map.size(); } bool empty() const { return m_map.empty(); } uint32 dump_size() const; void dump( stream& out ) const; protected: void insert( hash_type h, const value_type& str ) { NV_ASSERT_ALWAYS( str.size() < 0xFFF0, "String table can only hold strings up to 64k!" ); auto it = m_map.find( h ); if ( it != m_map.end() ) { // TODO : perform comparison check if in debug mode! return; } insert_raw( h, str.data(), static_cast( str.size() ) ); } size_type insert_raw( hash_type h, const char* str, length_type s ); value_type extract_raw( size_type index ) const { uint16 length = *reinterpret_cast( m_data.data() + index ); return value_type( m_data.data() + index + 2, length ); } indexer_type m_map; storage_type m_data; }; } #endif // NV_STL_STRING_TABLE_HH