/*
	ZName.hpp
	Author: James Russell <jcrussell@762studios.com>
	Created: 4/6/2011

	Purpose: 
	
	'Name' implementation, which is a bit like a ZBasicString but remains constant after 
	construction.  This allows for fast comparison and copy.

	In addition this allows the name to be compared to a hash of the name and determine equality.

	License:

	TODO

*/

#ifndef _ZNAME_H
#define _ZNAME_H

#include <ZSTL/ZString.hpp>

#include <ZUtil/ZUtilBuild.hpp>

//This is the maximum allowed length of a name
#ifndef ZNAME_MAX_LENGTH
#define ZNAME_MAX_LENGTH (128)
#endif

/*
ZName Implementation.
*/
class ZName
{
private:
	//The string
	char String[ZNAME_MAX_LENGTH + 1];

	//Length of the string
	size_t Length;

	//Hash of the string
	uint64_t Hash;

public:
	/*
	Constructor.
	*/
	ZName();

	/*
	Parameterized constructor.

	@param _string - the string name (null terminated)
	*/
	ZName(const char *_string);

	/*
	Parameterized constructor.

	@param _string - the string name
	*/
	explicit ZName(const ZString& _string);

	/*
	Parameterized constructor that takes the pre-computed hash value 
	for the name.  When a ZName is constructed in this fashion, the 
	ToString() function will return '<precomputed>'.

	@param _hash - the precomputed hash value for this string
	*/
	ZName(uint64_t _hash);

	/*
	Copy Constructor.

	@param _other - the other name
	*/
	ZName(const ZName& _other);

	/*
	Destructor.
	*/
	~ZName();

	/*
	= operator overload, that assigns this name to be another.

	@param _other - the name to assign this to
	@return - this name
	*/
	ZName& operator = (const ZName& _other);

	/*
	= operator overload, that assigns this name to be a string.

	@param _string - the string to create this name from
	@return - this name
	*/
	ZName& operator = (const ZString& _string);

	/*
	= operator overload, that assigns this name to be equal to a C-style string.

	@param _string - the string to create this name from
	@return - this name
	*/
	ZName& operator = (const char* _string);

	/*
	== operator.  Because names are constant, this is a fast comparison.

	@param _other - the name to compare this to
	@return - true if equal, false otherwise
	*/
	bool operator == (const ZName& _other) const;

	/*
	== operator for comparison with strings.  Less fast.

	@param _other - the string to compare this to
	@return - true if equal, false otherwise
	*/
	bool operator == (const ZString& _other) const;

	/*
	== operator.  Compares a name against hash value only.
	
	@param hash - the hash value to compare
	@return - true if equivalent hashes, false otherwise
	*/
	bool operator == (const ZHashValue hash) const;

	/*
	!= operator.  Because names are constant, this is a fast comparison.
	
	@param _other - the name to compare this to
	@return (bool) - true if not equal, false otherwise
	*/
	bool operator != (const ZName& _other) const;

	/*
	Hash code override.  Returns the (pre-computed) hash code.

	@return - hash code for this name
	*/
	operator ZHashValue () const;

	/*
	Returns this name as a string.

	@return (ZString) - this name as a ZString
	*/
	operator ZString () const;

	/*
	Gets this name as a string.

	@return (ZString) - this name as a ZString
	*/
	ZString ToString() const;

	/*
	Returns the string data for this name.

	@return (char*) - string data
	*/
	const char* Data() const;
};

#endif
