⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 stringc.c

📁 linux下的E_MAIL客户端源码
💻 C
📖 第 1 页 / 共 3 页
字号:
/* * $Id: StringC.C,v 1.6 2000/07/24 13:24:06 evgeny Exp $ * * Copyright (c) 1991 HaL Computer Systems, Inc.  All rights reserved. *  *          HAL COMPUTER SYSTEMS INTERNATIONAL, LTD. *                  1315 Dell Avenue *                  Campbell, CA  95008 * * Author: Greg Hilton * Contributors: Tom Lang, Frank Bieser, and others * * This program is free software; you can redistribute it and/or * modify it under the terms of the GNU General Public License * as published by the Free Software Foundation; either version 2 * of the License, or (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the * GNU General Public License for more details. * * http://www.gnu.org/copyleft/gpl.html * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA  02111-1307, USA. */#include <config.h>/* StringC.c -- implementation of character strings * *  Function: *  	 *  Class StringC implements character string objects.  Operations provided *  include & (concatenation) and () (substring extraction).  Type *  conversions between StringC and char* are provided, permitting the two *  to be used interchangeably in many contexts. * * */#include "StringC.h"#include "CharC.h"#include "StrCase.h"#include <unistd.h>extern int	debug1, debug2;/*----------------------------------------------------------------------- * Comparison method */static intcompare(const char *cs1, u_int len1, const char *cs2, u_int len2){   if ( (!cs1 && !cs2) || (len1 == 0 && len2 == 0) ) return  0;	// two nulls   if ( !cs1 || len1 == 0 )			     return -1;	// string1 null   if ( !cs2 || len2 == 0 )			     return  1;	// string2 null//// Check only up to the end of the shortest string//   u_int	minLen = MIN(len1, len2);   int		result = memcmp(cs1, cs2, minLen);//// If these first characters don't match return the result// If they do match and the lengths are equal, then return the result (0)//   if ( result != 0 || len1 == len2 ) return result;//// If they do match and the lengths are not equal, compare the lengths//   return (len1>len2 ? 1 : -1);} // End compare//---------------------------------------------------------------------------//  Null stringStringC StringC::Null;/*--------------------------------------------------------------------------- * Substring constructors */SubStringC::SubStringC(const StringC& s, unsigned pos, unsigned len){   init(s, pos, len);}SubStringC::SubStringC(const StringC& s, const RangeC& r){   init(s, r.firstIndex(), r.length());}SubStringC::SubStringC(SubStringC& ss){   _parent = ss._parent;   _subp   = ss._subp;   _sublen = ss._sublen;}/*--------------------------------------------------------------------------- * Method to initialize substring */voidSubStringC::init(const StringC& s, unsigned pos, unsigned len){   if ( pos >= s._len ) pos = len = 0;   if ( pos+len > s._len ) len = s._len - pos;   if ( s._p ) {      _subp   = &s._p[pos];      _sublen = len;   } else {      _subp   = 0;      _sublen = 0;   }   _parent = (StringC *)&s;} // End SubStringC init/*--------------------------------------------------------------------------- * Method to update memory allocation */voidStringC::reallocate(unsigned count, char shrinkOk){//// Allocate enough blocks to hold count chars plus the null terminator//   count++;   char growing   = (_alloc < count);   char shrinking = (shrinkOk && _alloc > 32 && count <= (_alloc>>1));//// If we're shrinking, reduce the block size until it becomes smaller than//    the amount to be allocated//   if ( shrinking ) {      while ( BLOCK_SIZE > count && BLOCK_SIZE > 32 )	 BLOCK_SIZE /= 2;   }//// See if we're reallocating//   if ( growing || shrinking ) {//// Count the number of memory blocks needed//      unsigned	blockSize = BLOCK_SIZE>0 ? BLOCK_SIZE : 32;      unsigned	blocks    = count / blockSize;      if ( count % blockSize ) blocks++;      if ( blocks < 1 ) blocks = 1;//// Increase the block size if necessary for next time//      if ( adjustBlock && BLOCK_SIZE < MAX_BLOCK_SIZE ) {         BLOCK_SIZE *= 2;	 if ( BLOCK_SIZE > MAX_BLOCK_SIZE ) BLOCK_SIZE = MAX_BLOCK_SIZE;      }      if ( debug2 ) {	 cout <<"StringC::reallocate:" 	    <<" _len=" << _len	    <<" _alloc=" << _alloc	    <<" count=" << count	    <<" new_alloc=" << blocks * blockSize	    <<endl;      }//// Allocate the memory//      _alloc = blocks * blockSize;      char *op = _p;      _p = new char[_alloc];//// Copy the old data if present//      if ( op ) {//// Copy only as much as will now fit//	 if ( _len >= count ) _len = count-1;	 memcpy(_p, op, _len);	 _p[_len] = 0;	 delete [] op;      }      else	 *_p = 0;   } // End if we need to reallocate} // End StringC::reallocate/*--------------------------------------------------------------------------- * Method to resize string */unsignedStringC::reSize(unsigned new_capacity){   reallocate(new_capacity, autoShrink);   return (_alloc-1);}/*--------------------------------------------------------------------------- * Replace this substring with the given string * The parent of this substring can be divided into 3 parts: * *           ------head-------- substring --tail-- *  String:  ccccccccccccccccccSSSSSSSSSSScccccccc * * The substring is replaced using this process: *    1) Copy head to another string *    2) Copy replacement to other string *    3) Copy tail to other string *    4) Copy other string to parent *    5) Reset substring length */voidSubStringC::ReplaceWith(const char *cs, u_int clen){   int	spos = position();	// start position of substring//// Save the part to the right of this substring (the tail)//   int		tpos = spos + _sublen;   int		tlen = _parent->length() - tpos;   StringC	tail = (*_parent)(tpos,tlen);//// If the source points into the destination, we've got to make copies//   if ( cs >= _parent->_p && cs <= _parent->_p + _parent->_len ) {      StringC	head = (*_parent)(0, spos);      StringC	body(clen); body.Set(cs, clen);      *_parent = head;      *_parent += body;      *_parent += tail;   }   else {//// Clear the parent from the start of this substring to the end//      _parent->Clear(spos);//// Add the new text and the tail//      _parent->Append(cs, clen);      *_parent += tail;   }} // End SubStringC ReplaceWithvoidSubStringC::operator=(const StringC& s){   ReplaceWith(s._p, s._len);}voidSubStringC::operator=(const SubStringC& ss){//// It's not clear what this method should do, but the latter is more useful//#if 1   _parent = ss._parent;   _subp   = ss._subp;   _sublen = ss._sublen;#else   ReplaceWith(ss._subp, ss._sublen);#endif}voidSubStringC::operator=(const CharC& c){   ReplaceWith(c.Addr(), c.Length());}voidSubStringC::operator=(const char* cs){   ReplaceWith(cs, cs ? strlen(cs) : 0);}/*--------------------------------------------------------------------------- * Substring concatentation */StringCSubStringC::operator+(const StringC& s){   StringC      t(_sublen + s._len);   if ( _subp ) memcpy(t._p, _subp, _sublen);   if ( s._p  ) memcpy(&t._p[_sublen], s._p, s._len);   t._len = _sublen + s._len;   t._p[t._len] = 0;   return (t);}StringCSubStringC::operator+(const SubStringC& ss){   StringC      s(ss);   return (operator+(s));}StringCSubStringC::operator+(const char* cs){   if (cs) {      StringC   s(cs);      return (operator+(s));   } else {      return ((StringC)*this);   }}/*--------------------------------------------------------------------------- * Methods to compare against substring */intSubStringC::compare(const StringC& s) const{   return ::compare(_subp, _sublen, s._p, s._len);}intSubStringC::compare(const SubStringC& ss) const{   return ::compare(_subp, _sublen, ss._subp, ss._sublen);}intSubStringC::compare(const char *cs) const{   return ::compare(_subp, _sublen, cs, cs?strlen(cs):0);}/*--------------------------------------------------------------------------- * Return position */unsignedSubStringC::position(){   return (_subp - _parent->_p);}/*--------------------------------------------------------------------------- * String initialization methods */voidStringC::init(){   _len       = 0;   _alloc     = 0;   _p         = NULL;}voidStringC::init(unsigned count){   init();   reallocate(count);   *_p = 0;}voidStringC::init(const char *cs){   if ( cs ) {      init((unsigned)strlen(cs));      strcpy(_p, cs);      _len = strlen(cs);   } else {      init();   }}voidStringC::init(const SubStringC& ss){   if ( ss._subp ) {      init(ss._sublen);      _len = ss._sublen;      memcpy(_p, ss._subp, _len);      _p[_len] = 0;   } else {      init();   }}voidStringC::init(const CharC& c){   if ( c.Addr() ) {      init(c.Length());      _len = c.Length();      memcpy(_p, c.Addr(), _len);      _p[_len] = 0;   } else {      init();   }}voidStringC::init(const StringC& s){   if ( s._p ) {      init(s._len);      _len = s._len;      memcpy(_p, s._p, _len);      _p[_len] = 0;   } else {      init();   }}/*--------------------------------------------------------------------------- * Method to give us ownership of an allocated string pointer */voidStringC::Own(const char *cs){   if ( _p ) delete [] _p;   _p     = (char*)cs;   _len   = cs ? strlen(cs) : 0;   _alloc = cs ? _len + 1   : 0;}/*--------------------------------------------------------------------------- * String assignment methods */voidStringC::Set(const char *cs, u_int clen){   if ( cs ) {//// If cs points into this string, make a copy//      if ( cs >= _p && cs <= (_p + _len) ) {	 CharC	data(cs, clen);	 StringC   t(data);	 *this = t;      }      else {//// If the new string is larger or if we're allowed to shrink and the new//   string requires less than half the allocated space, reallocate memory//	 if ( clen >= _alloc ||	      (autoShrink && _alloc > 32 && clen <= (_alloc>>1)) ) {	    if ( _p ) {	       delete [] _p;	       _p = NULL;	       _alloc = 0;	    }	    reallocate(clen, autoShrink);	 }	 _len = clen;	 memcpy(_p, cs, _len);	 _p[_len] = 0;      }   } // End if source address is valid   else {      if ( _p ) delete [] _p;      init();   }} // End Assign char* and lengthStringC&StringC::operator=(const StringC& s){   Set(s._p, s._len);   return *this;}StringC&StringC::operator=(const SubStringC& ss){   Set(ss._subp, ss._sublen);   return *this;}StringC&StringC::operator=(const CharC& c){   Set(c.Addr(), c.Length());   return *this;}StringC&StringC::operator=(const char *cs){   Set(cs, cs?strlen(cs):0);   return *this;}/*--------------------------------------------------------------------------- * String concatentation methods */voidStringC::Add(const char *p1, u_int len1, const char *p2, u_int len2, StringC& t)const{   if ( p1 ) memcpy(t._p, p1, len1);

⌨️ 快捷键说明

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