strclass.cpp

来自「经典c++程序的实现」· C++ 代码 · 共 515 行

CPP
515
字号

#include <iostream.h>
#include <string.h>
#include <stdlib.h>

#include "..\include\book.h"

#include "..\include\Strclass.h"


// allocate memory and copy a C++ String into the Object
String::String(char *s)  {     // constructors

	// length includes the NULL character
	size = strlen(s) + 1;

	// make room for string and NULL char and copy s.
	str = new char [size];
	// terminate program if memory is exhausted.
	if (str == NULL)
		Error(outOFMemory);
	strcpy(str, s);
}

// constructor; allocate memory and copy a String Object into the Object
String::String(const String& s) {
	// length includes the NULL character
	size = strlen(s.str) + 1;

	// make room for string and NULL char and copy s.
	str = new char [size];
	// terminate program if memory is exhausted.
	if (str == NULL)
		Error(outOFMemory);
	strcpy(str, s.str);	
}

String::~String(void) {          // destructor
	delete [] str;
}

// assignment operators

String& String::operator = (char *s)  {            // String = C++ String
	// if sizes differ, delete current string and reallocate
	if (int(strlen(s)+1) != size)  {
		delete [] str;
		str = new char [strlen(s) + 1];
		if (str == NULL)
			Error(outOFMemory);
		// assign size to be size of s
		size = strlen(s) + 1;
	}

	// copy s.str and return reference to current object
	strcpy(str, s);
	return *this;
}

String& String::operator = (const String& s)  {    // String = String	
/*
	// if sizes differ, delete current string and reallocate
	if (*this == s)
		return *this;

	if (s.size != size)  {
		delete [] str;
		str = new char [s.size];
		if (str == NULL)
			Error(outOFMemory);
		// assign size to be size of s
		size = s.size;
	}

	// copy s.str and return reference to current object
	strcpy(str, s.str);
	return *this;
*/
	if (*this == s)
		return *this;
	else {
	    *this = s.str;
	    return *this;
	}
}


// relational operators

// String == String, String == C++ String, C++ String == String

int String::operator == (const String& s) const {    // String == String
	return strcmp(str, s.str) == 0;
}

int String::operator == (char *s) const {			 //  String == C++ String
	return strcmp(str, s) == 0;
}

// C++ String == String. a friend function
// since C++ String on left
int operator == (char *str, const String& s) {		// C++ String == String
	return strcmp(str, s.str) == 0;
}

// String != String, String != C++ String, C++ String !=  String
int String::operator != (const String& s) const {	// String != String
	return strcmp(str, s.str) != 0;
}

int String::operator != (char *s) const {			 //  String != C++ String
	return strcmp(str, s) != 0;
}

// C++ String != String. a friend function
// since C++ String on left
int operator != (char *str, const String& s) {		// C++ String != String
	return strcmp(str, s.str) != 0;
}

// String < String, String < C++ String, C++ String < String
int String::operator < (const String& s) const {	// String < String
	return strcmp(str, s.str) < 0;
}

int String::operator < (char *s) const {			 //  String < C++ String
	return strcmp(str, s) < 0;
}

// C++ String < String. a friend function
// since C++ String on left
int operator < (char *str, const String& s) {		// C++ String < String
	return strcmp(str, s.str) < 0;
}

// String <= String, String <= C++ String, C++ String <= String
int String::operator <= (const String& s) const {	// String <= String
	return strcmp(str, s.str) <= 0;
}

int String::operator <= (char *s) const {			 //  String <= C++ String
	return strcmp(str, s) <= 0;
}

// C++ String <= String. a friend function
// since C++ String on left
int operator <= (char *str, const String& s) {	// C++ String <= String
	return strcmp(str, s.str) <= 0;
}

// String > String, String > C++ String, C++ String > String
int String::operator > (const String& s) const  {	// String > String
	return strcmp(str, s.str) > 0;
}

int String::operator > (char *s) const  {			 //  String > C++ String
	return strcmp(str, s) > 0;
}

// C++ String > String. a friend function
// since C++ String on left
int operator > (char *str, const String& s) {		// C++ String > String
	return strcmp(str, s.str) > 0;
}

// String >= String, String >= C++ String, C++ String >= String
int String::operator >= (const String& s) const {	// String >= String
	return strcmp(str, s.str) >= 0;
}

int String::operator >= (char *s) const  {			 //  String >= C++ String
	return strcmp(str, s) >= 0;
}

// C++ String >= String. a friend function
// since C++ String on left
int operator >= (char *str, const String& s)  {		// C++ String >= String
	return strcmp(str, s.str) >= 0;
}

// String concatenation operators

// String + C++ String, String + String, C++ String + String
// String += String, String += C++ String
String String::operator + (char *s) const {   // String + C++ String
	// build the new string with length len in temp
	String temp;
	int len;

	// delete the NULL string created when temp declared
	delete [] temp.str;

	// compute length of concatenated string and allocate memory in temp
	len = size + strlen(s);  // only one NULL terminator
	temp.str = new char [len];
	if (temp.str == NULL)
		Error(outOFMemory);

	// assign concatenated string size and build string
	temp.size = len;
	strcpy(temp.str, str);		// copy this->str to temp
	strcat(temp.str, s);        	// concatenate str
	return temp;			    	// return temp
}

String String::operator + (const String& s) const {   // string + string
	/*
	// build the new string with length len in temp	
	String temp;	
	int len;

	// delete the NULL string created when temp declared
	delete [] temp.str;

	// compute length of concatenated string and allocate memory in temp
	len = size + s.size - 1;  // only one NULL terminator
	temp.str = new char [len];
	if (temp.str == NULL)
		Error(outOFMemory);

	// assign concatenated string size and build string
	temp.size = len;
	strcpy(temp.str, str);		// copy str to temp
	strcat(temp.str, s.str);	// concatenate s.str
	return temp;
	*/

	return *this + s.str;				// return temp
}

String operator + (char *str, const String& s) {  // C++ String + String
	/*
	// build the new string with length len in temp
	String temp;
	int len;

    // delete the NULL string created when temp declared
	delete [] temp.str;

	// compute length of concatenated string and allocate memory in temp
	len = strlen(str) + s.size;  // only one NULL terminator
	temp.str = new char [len];
	if (temp.str == NULL)
		Error(outOFMemory);

	// assign concatenated string size and build string
	temp.size = len;
	strcpy(temp.str, str);		// copy str to temp
	strcat(temp.str, s.str);	// concatenate s.str
	return temp
	*/
	String temp;	

	temp = str;
	return temp + s;				// return temp
}

void String::operator += (const String& s) {    // String += String
	/*
	// build the new string with length len in temp	
	int len;
	char * temp;

    // remain the str
	temp = str;

	// compute length of concatenated string and allocate memory in temp
	len = size + s.size - 1;  // only one NULL terminator	
	str = new char [len];
	if (str == NULL)
		Error(outOFMemory);

	// assign concatenated string size and build string
	size = len;
	strcpy(str, temp);		// copy str to temp
	strcat(str, s.str);	// concatenate s.str
	*/
	*this = *this + s;
}

void String::operator += (char *s) {    // String += C++ String
	/*
	// build the new string with length len in temp	
	char* temp;
	int len;

	// remain the str
	temp = str;

	// compute length of concatenated string and allocate memory in temp
	len = size + strlen(s);  // only one NULL terminator
	str = new char [len];
	if (str == NULL)
		Error(outOFMemory);

	// assign concatenated string size and build string
	size = len;
	strcpy(str, temp);		// copy str to temp
	strcat(str, s);			// concatenate s.str
	*/
	*this = *this + s;
}

// String functions

// begin at start, find c
int String::Find(char c, int start) const {
	int i;

	for (i=start; i < size-1; i++) 
		if (str[i] == c)
			return i;
	return -1;
}

// find last occurrence of c
// return index of last occurrence of c in string
int String::FindLast(char c) const {
	int ret;
	char *p;

	// use C++ library function strrchr, returns pointer to 
	// the last occurrence of a character in the string
	p = strrchr(str, c);
	if (p != NULL)
		ret = int(p-str);     // compute index
	else 
		ret = -1;
	return ret;
}

// extract a substring
// return substring starting at index for count characters
String String::Substr(int index, int count) const {
	// number of charaters from index to end of string
	int charsLeft = size - index - 1,   i;

	// build substring in temp
	String temp;
	char *p,  *q;

	// return NULL string if index too large
	if (index >= size - 1)
		return temp;

	// if count > remaining chars, use remaining chars
	if (count > charsLeft)
		count = charsLeft;

	// delete the NUlL string created when temp declared
	delete [] temp.str;

	// allocate dynamic memory for the substring
	temp.str = new char [count+1];
	if (temp.str == NULL)
		Error(outOFMemory);

	// copy count chars from str to temp.str
	for (i=0, p=temp.str, q=&str[index];  i<count;  i++)
		*p++ = *q++;
	// NULL terminate
	*p = 0;

	temp.size = count + 1;
	return temp;
}

// insert a String to String
// insert from str[index]
void String::Insert(const String& s, int index) {	
	String left, right;

	left = Substr(0, index);
	right = Substr(index, size - index - 1);
	str = left + s + right;
}

// insert a C++ String
void String::Insert(char *s, int index)  {
	String temp;

	temp = s;
	Insert(s, index);
}

// delete a substring
// remove from str[index] to str[index+count-1]
void String::Remove(int index, int count)  {
	String left, right;
	
	left = Substr(0, index);
	right = Substr(index + count , (size - 1) - (index + count));
	str = left + right;
}

// String indexing

char& String::operator [] (int n)  {
	if (n >= 0 && n < size)
	  return str[n];
	else { 
		Error(indexError, n);
		return str[size-1];
	}
}

// convert String to C++ String
String::operator char* (void) const  {
	return str;
}

// String I/O
// a friend function
ostream& operator << (ostream& ostr, const String& s) {
	return ostr << s.str;
}

// a friend function
istream& operator << (istream& istr, String& s) {
	// read line into tmp
	char tmp[256];
	int  size;

	istr >> tmp;
	size = strlen(tmp) + 1;
	// delete string and allocate memory for new one
	delete [] s.str;
	s.str = new char [size];
	if (s.str == NULL)
		s.Error(outOFMemory);

	// copy tmp, return number of chars read
	strcpy(s.str, tmp);	
	return istr;
}

// read a line of text from stream istr
// read characters up to delimiter
int String::ReadString(istream& istr, char delimiter)  {
	// read line into tmp
	char tmp[256];

	// if not eof, read line of up to 255 characters
	if (istr.getline(tmp, 256, delimiter))  {
		// delete string and allocate memory for new one
		delete [] str;
		size = strlen(tmp) + 1;
		str = new char [size];
		if (str == NULL)
			Error(outOFMemory);

		// copy tmp, return number of chars read
		strcpy(str, tmp);
		return size-1;
	}
	else 
		return -1;				// return -1 on end of file
}

// additional methods
String::Length(void) const  {
	return size - 1;
}

int String::IsEmpty(void) const  {
	return str == NULL;
}

void String::Clear(void)  {
	delete [] str;
	str = NULL;
}

void Get_NextArr(const String pat, int next[]) {
	int i, k, len;

	len = pat.Length();
	next[0] = -1;    next[1] = 0;	
	if (pat[0] == pat[1])
		next[1] = next[0];

//	cout << pat << endl;
	i = 1;  k = 0;
//	cout << next [0] << " " << next[1];
    while (i<len-1) {
		while (k >= 0 && pat[k] != pat[i])
			k = next[k];
		i++;   k++;
		if (pat[k] == pat[i])
			next[i] = next[k];
		else next[i] = k;
//		cout << " " << next[i];
	}
//	cout << endl;
}

void Findpat(const String target, const String pat, int& index)  {
	int i=0, j=0, len_t, len_p, *next;

	len_t = target.Length();
	len_p = pat.Length();
	next = new int [len_t];

	Get_NextArr(pat, next);

	while (j < len_t && i < len_p) {
		if (i == -1 || target[j] == pat[i])  {
			j++;    i++;        // compare next pair of chars
		}
		else i = next[i];		// pat[i] compares with target[j]
	}
	if (i >= len_p)
		index = j - len_p;		// success, return start point
	else index = -1;			// failure, return -1;
}

⌨️ 快捷键说明

复制代码Ctrl + C
搜索代码Ctrl + F
全屏模式F11
增大字号Ctrl + =
减小字号Ctrl + -
显示快捷键?