int CString::CreateFromData(const char *data, long len) //根据data和长度len创建对象
{
Empty(); //清空
if (len <= 0)
return TRUE;
if (data == NULL)
return TRUE;
// actually, it's impossible
if (len > m_nSize)
return FALSE;
// copy data and set length
memcpy(m_pDataStart, data, len); //将字符数组复制给m_pDataStart指向内存空间
m_nLength = len;
m_pDataStart[m_nLength] = '\0';
m_pDataEnd = &(m_pDataStart[m_nLength]); //取得尾指针m_pDataEnd
return TRUE;
}
long CString::GetLength(void) const
{
return m_nLength;
}
int CString::IsEmpty(void) const
{
return !m_nLength;
}
int CString::Grow(int iBufferNum)
{
//unsigned char *pNewSpace = NULL;
if (iBufferNum <= 0)
return 0;
AssignNewSpace(m_nSize + iBufferNum * STR_PAGE_SIZE, 1); //分配新的内存空间,变为原来的两倍,移动1倍
return 1;
}
int CString::Append(const char *pSrc, int iLen)
{
int total_len;
char *pNewStart = NULL;
if (iLen <= 0)
return 0;
total_len = m_nLength + iLen; //append后的总的字符串长度
// if some space avaliable, defrag it firstly.
if (m_nSize > total_len) //如果原来总内存空间长度大于append后的字符串长度
{
//如果原来剩余空闲空间小于新添加子字符串的长度,而且
if (m_nSize - (m_pDataEnd - m_pBuffer) < iLen && m_pDataStart - m_pBuffer > 0) //而且m_pDataStart在m_pBuffer的后面
{
Defrag(); //调节原来的字符串
}
}
else //如果原来总内存空间长小于append后的字符串长度,需要开辟新空间
{
// allocate new memory space and copy orignal data
AssignNewSpace(total_len + 1, 1); //分配新的内存空间,变为原来的两倍,移动1倍
}
// get the merge point
pNewStart = m_pDataEnd; //将原来字符串的末尾指针转变成新添加子串的开始指针
if (!pNewStart)
return 0;
// copy data and adjust some pointers
memcpy(pNewStart, pSrc, iLen); //将新添加串pSrc放置在原来串联的末尾
m_nLength = total_len; //字符串的总长度变化
m_pDataStart[m_nLength] = 0; //新的字符串最后以为置为0
m_pDataEnd = &(m_pDataStart[m_nLength]); //让m_pDataEnd指向新的字符串的末尾指针
return 1;
}
void CString::Defrag(void)
{
// Sure! 重新初始化原来字符串头指针m_pDataStart,指向头部
memmove(m_pBuffer, m_pDataStart, m_nLength); //将m_pDataStart复制给m_pBuffer
// adjust those related pointers
m_pDataStart = m_pBuffer; //m_pDataStart指向m_pBuffer
m_pDataStart[m_nLength] = 0;
m_pDataEnd = &(m_pDataStart[m_nLength]); //重新获得原来的字符串尾指针m_pDataEnd
}
// Append another CString to this one
int CString::Append(CString *pNewStr)
{
char *pNewStart = NULL, *pSrc = NULL, *pDest = NULL;
int len = pNewStr->GetLength(); //新添加子串的长度
int total_len;
if (len <= 0)
return 0;
// const char *
pSrc = pNewStr->GetData(); //获得要添加的字符串的头指针
if (!pSrc)
return 0;
total_len = m_nLength + len; //新字符串的总长度 = 原来字符串长度 + 添加字符串长度
// if some space avaliable, defrag it firstly.
if (m_nSize - (m_pDataEnd - m_pBuffer) < len && m_pDataStart - m_pBuffer > 0)
{
Defrag();
}
// allocate new memory space
AssignNewSpace(total_len + 1, 1); // //根据total_len分配新的内存空间
// get the merge point
pNewStart = m_pDataEnd; //将原来字符串的末尾指针转变成新添加子串的开始指针
if (!pNewStart)
return 0;
// copy data and adjust some pointers
memcpy(pNewStart, pSrc, len); //将新添加串pSrc放置在原来串联的末尾
m_nLength = total_len;
m_pDataStart[m_nLength] = 0;
m_pDataEnd = &(m_pDataStart[m_nLength]); //让m_pDataEnd指向新的字符串的末尾指针
return 1;
}
// Adjust start and end pointer of its buffer
// Get one character at give position
char CString::GetAt(int nIndex) const
{
if (nIndex >= m_nLength)
return -1;
if (nIndex < 0)
return -1;
return m_pDataStart[nIndex];
}
// return single character at zero-based index
char CString::operator[](int nIndex) const
{
if (nIndex >= m_nLength)
return -1;
return m_pDataStart[nIndex];
}
// return pointer to const string
CString::operator LPCTSTR() const //将该字符串转变为const char*字符串常量
{
return (const char*)m_pDataStart;
}
// duplicate a string
CString *CString::Duplicate(int iBufferNum) const
{
CString *pCStr = NULL;
pCStr = new CString(m_pDataStart, m_nLength, iBufferNum);
return pCStr;
}
// copy from another CString
const CString& CString::operator=(CString& stringSrc) //赋值操作符
{
long len = stringSrc.GetLength(); //取得stringSrc字符串长度
if (len >= m_nSize) //如果空间大小不够
{
AssignNewSpace(len + 1, 0); // don't copy orignal data //将会申请一块新的内存空间
}
// copy data and adjust pointers
Empty(); //清空
memcpy(m_pDataStart, stringSrc.GetData(), len); //将字符串stringSrc复制给新的m_pDataStart
m_pDataStart[len] = 0;
m_pDataEnd = &(m_pDataStart[len]); //获得新的m_pDataEnd
m_nLength = len;
return *this;
}
// set string content to single character
CString &CString::operator=(char c) //赋值操作符,将字符赋给字符串
{
if (m_nSize < 2) // c + '\0' length //如果内存空间不足
{ // it needs to realloc space, but we use new and delete pair
SafeDestroy();
m_pBuffer = new char[2]; //重新申请内存
m_nSize = 2;
//TODO, I don't check the value of this pointer, unkown result. :)
}
m_pDataStart = m_pBuffer; //获得头指针
m_pDataStart[0] = c;
m_pDataStart[1] = 0;
m_pDataEnd = &(m_pDataStart[1]); //获得尾指针
m_nLength = 1;
return *this;
}
// Set one character at give position
void CString::SetAt(long pos, char ch)
{
if (pos < m_nLength)
m_pDataStart[pos] = ch;
return;
}
// Get the string started from give position
void CString::GetManyChars(char *buf, long pos, long len) const
{
if (buf == NULL)
return;
if (pos >= m_nLength)
return;
if (pos + len > m_nLength)
len = m_nLength - pos;
if (len > 0)
memcpy(buf, m_pDataStart + pos, len); //将 m_pDataStart + pos开始长为len的子串复制给buf
}
// Compare itself with a new string, case-sensitive
int CString::Compare(const char *pNewStr) const
{
if (pNewStr == NULL)
return -1;
return strcmp(m_pDataStart, pNewStr);
}
// Compare itself with a new string, case-ignored
int CString::CompareNoCase(const char *pNewStr) const
{
if (pNewStr == NULL)
return -1;
#ifndef WIN32
return strcasecmp(m_pDataStart, pNewStr);
#else
return stricmp(m_pDataStart, pNewStr);
#endif
}
// find a character start from a give position
int CString::Find(int ch, long pos) const
{
char *p = NULL;
if (ch < 0)
return -1;
if (ch > UCHAR_MAX)
return -1;
if (pos < 0)
return -1;
if (pos >= m_nLength)
return -1;
p = (char*)memchr(m_pDataStart + pos, ch, m_nLength - pos);
if (!p)
return -1;
return p - m_pDataStart;
}
// find a string start from a give position
int CString::Find(const char *str, long pos) const
{
long len;
char *p = NULL;
if (str == NULL)
return -1;
len = strlen(str);
if (len == 0)
return 0;
p = (char *)strstr(m_pDataStart + pos, str);
if (p == NULL)
return -1;
else
return p - m_pDataStart;
}
char *CString::GetBuffer(int nMinBufLength) //获得该字符串头指针,并且说明返回的内存空间最小值
{
Defrag();
if (nMinBufLength > m_nLength)
AssignNewSpace(nMinBufLength, 1);
return m_pDataStart;
}
void CString::ReleaseBuffer(int nNewLength)
{
return;
}
//Extracts the left part of a string.
CString CString::Left(int count) const
{
if (count < 0)
count = 0;
if (count >= m_nLength)
return *this;
CString dest(m_pDataStart, count); //调用构造函数新建一个
return dest;
}
//Extracts the right part of a string.
CString CString::Right(int count) const
{
if (count < 0)
count = 0;
if (count >= m_nLength)
return *this;
CString dest(&(m_pDataStart[m_nLength - count]), count);
return dest;
}
//Converts all the characters in this string to uppercase characters.
void CString::MakeUpper(void)
{
strupr(m_pDataStart);
}
//Converts all the characters in this string to lowercase characters.
void CString::MakeLower(void)
{
strlwr(m_pDataStart);
}
// TODO: check the space left in the two pading of the whole buffer
// trim the left spaces
void CString::TrimLeft(void) // //将字符串右边的空格去掉
{
int start = 0;
while (isspace(m_pDataStart[start]) && start < m_nLength)
start ++;
if (start > 0)
{
m_pDataStart += start;
}
}