c++ string的简单实现

本文详细介绍了C++标准中string类的简单实现,包括构造函数、赋值运算符、比较运算符、拼接运算符以及访问字符串元素等功能。

c++标准中的string采用模板实现,扩展性比较好;下面的代码简单实现了string类。


/*
 *  CCString.h
 *  c++_common_codes
 *
 *  Created by xichen on 12-1-11.
 *  Copyright 2012 cc_team. All rights reserved.
 *
*/

#ifndef CC_STRING_BASE_H
#define CC_STRING_BASE_H

// #include "ccIOBase.h"
#include <iostream>

using namespace std;

class CCString
{
public:
	CCString();
	~CCString();

	CCString(const CCString & newStr);
	CCString(const char * charStr);
	
public:
	CCString &operator=(const CCString & newStr);
	CCString &operator=(const char * newStr);

public:
	friend bool operator==(const CCString &leftStr, const CCString &rightStr);
	friend bool operator==(const CCString &leftStr, const char *rightCharStr);
	friend bool operator==(const char *leftCharStr, const CCString &rightStr);
	
	friend bool operator!=(const CCString &leftStr, const CCString &rightStr);
	friend bool operator!=(const CCString &leftStr, const char *rightCharStr);
	friend bool operator!=(const char *leftCharStr, const CCString &rightStr);
	
	friend bool operator>(const CCString &leftStr, const CCString &rightStr);
	friend bool operator>(const CCString &leftStr, const char *rightCharStr);

	friend bool operator<(const CCString &leftStr, const CCString &rightStr);
	friend bool operator<(const CCString &leftStr, const char *rightCharStr);

	friend bool operator>=(const CCString &leftStr, const CCString &rightStr);
	friend bool operator>=(const CCString &leftStr, const char *rightCharStr);

	friend bool operator<=(const CCString &leftStr, const CCString &rightStr);
	friend bool operator<=(const CCString &leftStr, const char *rightCharStr);

public:
	friend CCString operator+(const CCString &leftStr, const CCString &rightStr);
	friend CCString operator+(const CCString &leftStr, const char *rightCharStr);

	CCString & operator+=(const CCString &newStr);
	CCString & operator+=(const char *rightCharStr);

public:
	friend ostream & operator<<(ostream & os, const CCString & ccStr);
	friend istream & operator>>(istream & is, CCString & ccStr);

public:
	char	& operator[](int index);
	const char &operator[](int index) const;
	operator char * ();

public:
	char	* pointer() const;
	char	* c_str() const;
	int		length() const;
	bool	empty() const;

private:
	char	*str;
	int		len;
};

#endif

/*
 *  CCString.cpp
 *  c++_common_codes
 *
 *  Created by xichen on 12-1-11.
 *  Copyright 2012 cc_team. All rights reserved.
 *
*/

#include "ccStringBase.h"
#include <cstring>

CCString::CCString()
{
	str = new char[1];
	str[0] = '\0';
	len = 0;
}

CCString::CCString( const CCString &newStr )
{
	if(this == &newStr)
	{
		return;
	}

	int newStrLen = newStr.length();
	str = new char[newStrLen + 1];
	::memcpy(str, newStr.pointer(), newStrLen);
	str[newStrLen] = '\0';
	len = newStrLen;
}

CCString::CCString( const char * charStr )
{
	int newStrLen = strlen(charStr);
	str = new char[newStrLen + 1];
	::memcpy(str, charStr, newStrLen);
	str[newStrLen] = '\0';
	len = newStrLen;
}

CCString::~CCString()
{
	delete []str;
}

CCString & CCString::operator=( const CCString &newStr )
{
	if(this == &newStr)
		return *this;

	delete str;
	int newStrLen = newStr.length();
	str = new char[newStrLen + 1];
	::memcpy(str, newStr.pointer(), newStrLen);
	str[newStrLen] = '\0';
	len = newStrLen;
	return *this;
}

CCString & CCString::operator=(const char *newStr)
{
	delete str;
	int newStrLen = ::strlen(newStr);
	str = new char[newStrLen + 1];
	::memcpy(str, newStr, newStrLen);
	str[newStrLen] = '\0';
	len = newStrLen;
	return *this;
}

char	* CCString::pointer() const
{
	return str;
}

int CCString::length() const
{
	return len;
}

CCString & CCString::operator+=( const CCString &newStr )
{
	int newStrLen = newStr.length();
	if(newStrLen > 0)
	{
		int currStrNewLen = len + newStrLen;
		char * newCharStr = new char[currStrNewLen + 1];
		if(newCharStr)
		{
			strcpy(newCharStr, str);
			strcat(newCharStr, newStr.pointer());
			
			delete str;
			str = newCharStr;
			len = currStrNewLen;
		}
		else
		{
			throw "NoEnoughMemoryException";
		}
	}
	return *this;
}

CCString & CCString::operator+=( const char *rightCharStr )
{
	int newStrLen = strlen(rightCharStr);
	if(newStrLen > 0)
	{
		int currStrNewLen = len + newStrLen;
		char * newCharStr = new char[currStrNewLen + 1];
		if(newCharStr)
		{
			strcpy(newCharStr, str);
			strcat(newCharStr, rightCharStr);

			delete str;
			str = newCharStr;
			len = currStrNewLen;
		}
		else
		{
			throw "NoEnoughMemoryException";
		}
	}
	return *this;
}

char & CCString::operator[]( int index )
{
	return str[index];
}

const char & CCString::operator[]( int index ) const
{
	return str[index];
}

CCString::operator char * ()
{
	return str;
}

char	* CCString::c_str() const
{
	return str;
}

bool CCString::empty() const
{
	return (len == 0);
}

bool operator==( const CCString &leftStr, const CCString &rightStr )
{
	if(leftStr.pointer() == rightStr.pointer())
		return true;
	return (!strcmp(leftStr.pointer(), rightStr.pointer()));
}

bool operator==( const CCString &leftStr, const char *rightCharStr )
{
	if(leftStr.pointer() == rightCharStr)
		return true;
	return (!strcmp(leftStr.pointer(), rightCharStr));
}

bool operator==(const char *leftCharStr, const CCString &rightStr)
{
	return operator==(rightStr, leftCharStr);
}

bool operator!=( const CCString &leftStr, const CCString &rightStr )
{
	return !(operator==(leftStr, rightStr));
}

bool operator!=( const CCString &leftStr, const char *rightCharStr )
{
	return !(operator==(leftStr, rightCharStr));
}

bool operator!=( const char *leftCharStr, const CCString &rightStr)
{
	return !(operator==(rightStr, leftCharStr));
}

bool operator>( const CCString &leftStr, const CCString &rightStr )
{
	if(leftStr.pointer() == rightStr.pointer())
		return false;
	return (strcmp(leftStr.pointer(), rightStr.pointer()) > 0);
}


bool operator>( const CCString &leftStr, const char *rightCharStr )
{
	if(leftStr.pointer() == rightCharStr)
		return false;
	return (strcmp(leftStr.pointer(), rightCharStr) > 0);
}


bool operator<( const CCString &leftStr, const CCString &rightStr )
{
	if(leftStr.pointer() == rightStr.pointer())
		return false;
	return (strcmp(leftStr.pointer(), rightStr.pointer()) < 0);
}


bool operator<( const CCString &leftStr, const char *rightCharStr )
{
	if(leftStr.pointer() == rightCharStr)
		return false;
	return (strcmp(leftStr.pointer(), rightCharStr) < 0);
}


bool operator>=( const CCString &leftStr, const CCString &rightStr )
{
	if(leftStr.pointer() == rightStr.pointer())
		return true;
	return (strcmp(leftStr.pointer(), rightStr.pointer()) >= 0);
}


bool operator>=( const CCString &leftStr, const char *rightCharStr )
{
	if(leftStr.pointer() == rightCharStr)
		return true;
	return (strcmp(leftStr.pointer(), rightCharStr) >= 0);
}


bool operator<=( const CCString &leftStr, const CCString &rightStr )
{
	if(leftStr.pointer() == rightStr.pointer())
		return true;
	return (strcmp(leftStr.pointer(), rightStr.pointer()) <= 0);
}


bool operator<=( const CCString &leftStr, const char *rightCharStr )
{
	if(leftStr.pointer() == rightCharStr)
		return true;
	return (strcmp(leftStr.pointer(), rightCharStr) <= 0);
}


CCString operator+( const CCString &leftStr, const CCString &rightStr )
{
	int leftStrLen = leftStr.length();
	int rightStrLen = rightStr.length();
	CCString str;

	char * newCharStr = new char[leftStrLen + rightStrLen + 1];
	if(newCharStr)
	{
		strcpy(newCharStr, leftStr.pointer());
		strcat(newCharStr, rightStr.pointer());
		str = newCharStr;
		delete []newCharStr;
		return str;
	}
	else
	{
		throw "NoEnoughMemoryException";
	}
}


CCString operator+( const CCString &leftStr, const char *rightCharStr )
{
	int leftStrLen = leftStr.length();
	int rightStrLen = strlen(rightCharStr);
	CCString str;

	char * newCharStr = new char[leftStrLen + rightStrLen + 1];
	if(newCharStr)
	{
		strcpy(newCharStr, leftStr.pointer());
		strcat(newCharStr, rightCharStr);
		str = newCharStr;
		delete []newCharStr;
		return str;
	}
	else
	{
		throw "NoEnoughMemoryException";
	}
}

ostream & operator<<( ostream & os, const CCString & ccStr )
{
	os << ccStr.str;
	return os;
}


istream & operator>>( istream & is, CCString & ccStr )
{
	ccStr.str = new char[128];		// I am sorry, but I don't know the exact buffer size, 128 is just thought just now.
	is >> ccStr.str;
	ccStr.len = strlen(ccStr.str);

	return is;
}


简单测试代码:

#include "ccTestStringBase.h"


void ccTestStringBase()
{
#if 1 || ENABLE_ALL_TEST	// CCString
	CCString str;
	//COUT_LINE(str.pointer())
	//COUT_LINE(str.length())
	CC_ASSERT_EQUAL(str, "", "Not equal");
	CC_ASSERT_EQUAL(str.length(), 0, "Not equal");

	str = "xichen";
	//COUT_LINE(str.pointer())
	//COUT_LINE(str.length())
	CC_ASSERT_EQUAL(str, "xichen", "Not equal");
	CC_ASSERT_EQUAL(str.length(), strlen("xichen"), "Not equal");

	CCString str1 = str;
	//COUT_LINE(str1.pointer())
	CC_ASSERT_EQUAL(str1, "xichen", "Not equal");

	/*
	COUT_LINE(str == str1)
	COUT_LINE(str != str1)
	COUT_LINE(str == "xichen2")
	COUT_LINE(str != "xichen2")

	COUT_LINE(str > str1)
	COUT_LINE(str < str1)
	COUT_LINE(str >= str1)
	COUT_LINE(str <= str1)
	COUT_LINE(str > "xichen2")
	COUT_LINE(str < "xichen2")
	COUT_LINE(str >= "xichen2")
	COUT_LINE(str <= "xichen2")
	*/

	CC_ASSERT(str == str1, "Not right");
	CC_ASSERT_EQUAL(str != str1, 0, "Not right");
	CC_ASSERT_EQUAL(str == "xichen2", 0, "Not right");
	CC_ASSERT_EQUAL(str != "xichen2", 1, "Not right");
	CC_ASSERT_EQUAL(str > str1, 0, "Not right");
	CC_ASSERT_EQUAL(str < str1, 0, "Not right");
	CC_ASSERT_EQUAL(str >= str1, 1, "Not right");
	CC_ASSERT_EQUAL(str <= str1, 1, "Not right");
	CC_ASSERT_EQUAL(str > "xichen2", 0, "Not right");
	CC_ASSERT_EQUAL(str < "xichen2", 1, "Not right");
	CC_ASSERT_EQUAL(str >= "xichen2", 0, "Not right");
	CC_ASSERT_EQUAL(str <= "xichen2", 1, "Not right");

	
	CCString str2 = str + str1;
	//COUT_LINE(str2.pointer())
	CC_ASSERT_EQUAL(str2, "xichenxichen", "Not right");
	CC_ASSERT_EQUAL("xichenxichen", str2, "Not right");
	CC_ASSERT_EQUAL("xichenxichen" == str2, 1, "Not equal");
	
	str2 = str2 + " xuchen";
	//COUT_LINE(str2.pointer())
	CC_ASSERT_EQUAL(str2, "xichenxichen xuchen", "Not right");

	str2 += "ok";
	//COUT_LINE(str2.pointer())
	CC_ASSERT_EQUAL(str2, "xichenxichen xuchenok", "Not right");
	
	str2 += str;
	//COUT_LINE(str2.pointer())
	CC_ASSERT_EQUAL(str2, "xichenxichen xuchenokxichen", "Not right");

	//CC_ASSERT(1 == 2, "Not right");

	CCString str3;
	// cin >> str3;
	// COUT_LINE(str3)

	CC_ASSERT(str[2] == 'c', "not right");
	str[2] = 'd';
	CC_ASSERT(str[2] == 'd', "not right");

	// COUT_LINE((char *)str2)

	CC_ASSERT(str.empty() != true, "not right");
	CC_ASSERT(str3.empty() == true, "not right");
#endif
}



CC_ASSERT和CC_ASSERT_EQUAL宏定义为:

#ifdef _WINDOWS
#define CC_ASSERT(var, msg)	\
{	\
	CCString strTemp19870814_neverUsed;	\
	char line[32] = {0};	\
	strTemp19870814_neverUsed += __FILE__, strTemp19870814_neverUsed += " Line:", itoa(__LINE__, line, 10), strTemp19870814_neverUsed += line;	\
	if(!(var))	COUT_2_VAR_ENDL(strTemp19870814_neverUsed.pointer(), (msg))	\
	else				COUT_LINE("OK!")	\
}

#define CC_ASSERT_EQUAL(var1, var2, msg)	\
	{	\
		CCString strTemp19870814_neverUsed;	\
		char line[32] = {0};	\
		strTemp19870814_neverUsed += __FILE__, strTemp19870814_neverUsed += " Line:", itoa(__LINE__, line, 10), strTemp19870814_neverUsed += line;	\
		if((var1) != (var2))	COUT_2_VAR_ENDL(strTemp19870814_neverUsed.pointer(), (msg))	\
		else				COUT_LINE("OK!")	\
	}

#else
#define CC_ASSERT(var, msg)	\
{	\
	CCString strTemp19870814_neverUsed;	\
	char line[32] = {0};	\
	strTemp19870814_neverUsed += __FILE__, strTemp19870814_neverUsed += " Line:", sprintf(line, "%d",__LINE__), strTemp19870814_neverUsed += line;	\
	if(!(var))	COUT_2_VAR_ENDL(strTemp19870814_neverUsed.pointer(), (msg))	\
	else				COUT_LINE("OK!")	\
}

#define CC_ASSERT_EQUAL(var1, var2, msg)	\
{	\
CCString strTemp19870814_neverUsed;	\
char line[32] = {0};	\
strTemp19870814_neverUsed += __FILE__, strTemp19870814_neverUsed += " Line:", sprintf(line, "%d",__LINE__), strTemp19870814_neverUsed += line;	\
if((var1) != (var2))	COUT_2_VAR_ENDL(strTemp19870814_neverUsed.pointer(), (msg))	\
else				COUT_LINE("OK!")	\
}
#endif

COUT_LINE宏定义为:

#define COUT_LINE(str)		std::cout << (str) << std::endl;

注:欢迎提出代码中的问题,不甚感激;


评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值