/**
* @brief
�̰߳�ȫģ����

* @version
  V 1.0.0

* @author
  ���濡

* @date
  ����ʱ��:  2018-08-20\n

* @note
  2018-08-20  �����ࡣ\n

* @warning

* @bug
  
*/

#pragma once

#include <map>
#include <stdint.h>
#include <boost/thread/mutex.hpp>

template<class Key, class T>
class thread_safe_map
{
private:
	std::map<Key, T> __map;
	mutable boost::mutex the_mutex;
public:
	/**
	* @brief
	���ú�����

	* @param  [in] const Key &inputKey  key\n
	* @param  [in] const T &inputValue  value\n

	* @return ��\n

	* @note

	* @warning

	* @bug

	*/
	void insert( const Key &inputKey, const T &inputValue )
	{
		boost::mutex::scoped_lock lock( the_mutex );
		__map.insert( std::pair<Key, T>( inputKey, inputValue ) );
		lock.unlock();
	}
	/**
	* @brief
	����map�Ƿ�Ϊ�պ�����

	* @param  ��\n

	* @return �Ƿ�Ϊ��\n
	* @retval  true  ��\n
    * @retval  false  ����\n

	* @note

	* @warning

	* @bug

	*/
	bool empty() const 
	{
		boost::mutex::scoped_lock lock( the_mutex );
		return __map.empty();
	}
	/**
	* @brief
	��ij��key��ȡֵ�ĺ�����

	* @param  [in] const Key &inputKey  ָ����key\n
	* @param  [out] T &outputValue  ��õ�ֵ\n

	* @return �Ƿ��ȡ�ɹ�\n
	* @retval  true  �ɹ�\n
    * @retval  false  ʧ��\n

	* @note

	* @warning

	* @bug

	*/
	bool get( const Key &inputKey, T &outputValue ) 
	{
		boost::mutex::scoped_lock lock( the_mutex );

		typename std::map<Key, T>::iterator it;
		it = __map.find( inputKey );

		if ( __map.end() == it ) 
		{
			return false;
		}

		outputValue = it->second;
		return true;
	}
	/**
	* @brief
	����ij��key��Ӧֵ�ĺ�����

	* @param  [in] const Key &inputKey  ָ����key\n
	* @param  [out] T &outputValue  ��õ�ֵ\n

	* @return �Ƿ��ȡ�ɹ�\n
	* @retval  true  �ɹ�\n
    * @retval  false  ʧ��\n

	* @note

	* @warning

	* @bug

	*/
	bool update( const Key &inputKey, const T &inputValue )
	{
		boost::mutex::scoped_lock lock( the_mutex );

		typename std::map<Key, T>::iterator it;
		it = __map.find( inputKey );

		if ( __map.end() == it ) 
		{
			return false;
		}

		it->second = inputValue;
		return true;
	}
	/**
	* @brief
	����ij��keyɾ��ֵ�ĺ�����

	* @param  [in] const Key &inputKey  ָ����key\n

	* @return ��\n

	* @note

	* @warning

	* @bug

	*/
	void erase( const Key &inputKey )
	{
		boost::mutex::scoped_lock lock( the_mutex );
		__map.erase( inputKey );
	}
	/**
	* @brief
	��ô�С�ĺ�����

	* @param  ��\n

	* @return ��\n

	* @note

	* @warning

	* @bug

	*/
	size_t size() const
	{
		boost::mutex::scoped_lock lock( the_mutex );
		return __map.size();
	}
	/**
	* @brief
	���map�����

	* @param  ��\n

	* @return ��\n

	* @note

	* @warning

	* @bug

	*/
	void clear()
	{
		boost::mutex::scoped_lock lock( the_mutex );
		__map.clear();
	}
	/**
	* @brief
	����map�����

	* @param  ��\n

	* @return ��\n

	* @note

	* @warning

	* @bug

	*/
	void copy( std::map<Key, T>& dest_map )
	{
		boost::mutex::scoped_lock lock( the_mutex );
		dest_map = __map;
	}
};