Main Page | Namespace List | Class Hierarchy | Alphabetical List | Class List | Directories | File List | Namespace Members | Class Members | File Members | Related Pages

AString.cpp

Go to the documentation of this file.
00001 // *****************************************************************
00002 // UGA        version        1.0        --       November       1992
00003 // *****************************************************************
00004 
00005 // This  code is part of a preliminary release of UGA (uni-processor
00006 // genetic  algorithm)  and  associated  class  libraries.   It  was
00007 // developed  on  Sun Sparcstations using AT&T's C++ compiler.  Ver-
00008 // sions which will compile using the GNU C++  compiler  on  various
00009 // architectures are in preparation.
00010 
00011 // This software was developed and tested at  various  institutions,
00012 // including  Amoco  Production  Company's  Tulsa  Research  Center,
00013 // Princeton University, The University of Paris, and Los Alamos Na-
00014 // tional Laboratories.  The authors wish to express their gratitude
00015 // to these institutions for encouraging this work.
00016 
00017 // You get this code for free.
00018 
00019 // You can do anything you want with it, including make a fortune.
00020 
00021 // Neither the authors, Amoco, nor anyone else you can imagine makes
00022 // any  promises or guarantees about anything in this package or any
00023 // aspect of its functionality.
00024 
00025 // Authors:  Martin L. Smith, Terri L. Fischer
00026 
00027 // For    further    information    contact    John    Scales     at
00028 // jscales@dix.mines.colorado.edu,  telephone:   303-273-3408,  fax:
00029 // 303-273-3478.  
00030 
00031 // This may look like C code, but it is really -*- C++ -*-
00032 
00033 #include "AString.hh"
00034 #include <string.h>
00035 #include <ctype.h>
00036 #include <stdlib.h>
00037 #include <stdio.h>
00038 
00039 namespace coool 
00040 {
00041     using namespace coool;
00042 
00043 
00044 static const int        default_chunk_size = 8;
00045 static const char*      myNameIs = "AString";
00046 static const char*      empty_string = "";
00047 
00048 // private methods
00049 void AString::bigEnough(const int size)
00050 {
00051     if(size < 0){
00052         cerr << className() << "bigEnough: arg size = " << size
00053             << " is less than zero." << endl;
00054         exit(1);
00055         }
00056     
00057     if(size >= 0 && mem < (size + 1)){
00058         char* tmp = contents;
00059         
00060         // have to do division before multiplication because
00061         // we're doing integer arithmetic and we want the division
00062         // step to truncate the answer
00063         
00064         int num_chunks = ((size + 1) + (chunksize() - 1)) / chunksize();
00065         mem = num_chunks * chunksize();
00066         contents = new char[mem];
00067         contents[0] = '\0';
00068         
00069         if(tmp != NULL)
00070             strcpy(contents, tmp);
00071         delete tmp;
00072     }
00073 }
00074 
00075 void AString::initVars() {
00076     length(0);
00077     mem = 0;
00078     contents = NULL;
00079     chunksize(default_chunk_size);
00080 }
00081 
00082 int AString::inRange(const long i) const {
00083     return(i >= 0 && i < length());
00084 }
00085 
00086 void AString::length(const int new_length){
00087     len = new_length >= 0 ? new_length : -1;
00088 }
00089 
00090 // protected methods
00091 
00092 // Description:
00093 // Converts a single char into an AString.  Be warned that it will
00094 // also convert numbers (\fIe.g.\fP 7) into an AString as well.
00095 AString::AString(const char c){
00096     initVars();
00097     copy(c);
00098 }
00099 
00100 // Description:
00101 // Called by the equality operators. Returns an integer greater than,
00102 // equal to, or less than 0, according as the current AString is
00103 // lexicographically greater than, equal to, or less than the AString
00104 // argument \fIas\fP.
00105 int AString::compare(const AString& as) const{
00106     if(this == &as)             // they're the same AString
00107         return 0;
00108     int asIsEmpty       = as.empty();
00109     int thisIsEmpty     = empty();
00110     
00111     if(asIsEmpty && thisIsEmpty) // both are empty
00112         return 0;                // contents == as.contents
00113     else if(asIsEmpty || thisIsEmpty) // only one is empty
00114         return asIsEmpty ? 1 : -1;
00115     else                              // neither are empty
00116         return strcmp(contents, as.contents);
00117 }
00118 
00119 // Description:
00120 // Called by the equality operators. Returns an integer greater than,
00121 // equal to, or less than 0, according as the current AString is
00122 // lexicographically greater than, equal to, or less than the const char*
00123 // argument \fIs\fP.
00124 int AString::compare(const char* s) const {
00125     if(contents == s)
00126         return 0;               // they're the same pointer
00127     
00128     int sIsEmpty = (s == NULL ? True : (strlen(s) == 0 ? TRUE : FALSE));
00129     int thisIsEmpty = empty();
00130 
00131     if(sIsEmpty && thisIsEmpty) // both are empty
00132         return 0;                // s == as.s
00133     else if(sIsEmpty || thisIsEmpty) // only one is empty
00134         // sIsEmpty ? contents > s : contents < s
00135         return sIsEmpty ? 1 : -1;
00136     else                             // neither are empty
00137         return strcmp(contents, s);
00138 }
00139 
00140 // Description:
00141 // Appends the contents of the AString argument \fIas\fP to the end of
00142 // the current AString.
00143 void AString::concat(const AString& as){
00144     if(!as.empty()){
00145         int this_length = length();
00146         int as_length   = as.length();
00147         int m           = this_length + as_length;
00148         bigEnough(m);           // make bigEnough before assigning pointer
00149         char* start_pointer = &contents[this_length];
00150         length(m);
00151 
00152         // do strncpy (instead of strcpy) in case as is same AString as this
00153         strncpy(start_pointer, as.contents, as_length);
00154         contents[m] = '\0';
00155     }
00156 }
00157 
00158 // Description:
00159 // Appends the contents of the const char* argument \fIs\fP to the end
00160 // of the current AString.
00161 void AString::concat(const char* s){
00162     if(s != NULL){
00163         int this_length = length();
00164         int s_length    = strlen(s);
00165         int m           = this_length + s_length;
00166         bigEnough(m);           // make bigEnough before assigning pointer
00167         char* start_pointer = &contents[this_length];
00168         length(m);
00169         strncpy(start_pointer, s, s_length);
00170         contents[m] = '\0';
00171     }
00172 }
00173         
00174 // Description:
00175 // Appends the const char argument \fIc\fP to the end of the current
00176 // AString.
00177 void AString::concat(const char& c){
00178     int m = length();
00179     bigEnough(m + 1);
00180     contents[m++] = c;
00181     contents[m] = '\0';
00182     length(m);
00183 }
00184 
00185 // Description:
00186 // Replaces the old contents of the current AString with the contents
00187 // of the AString argument \fIas\fP.
00188 void AString::copy(const AString& as){
00189     if(this != &as)             // if they're not the same AString
00190         if(!as.empty()){
00191             length(as.length());
00192             bigEnough(length());
00193             strcpy(contents, as.contents);
00194         }
00195 }
00196 
00197 // Description:
00198 // Replaces the old contents of the current AString with the contents
00199 // of the const char* argument \fIcp\fP.
00200 void AString::copy(const char* cp){
00201     if(contents != cp)          // if they're not the same pointer
00202         if(cp != NULL){
00203             length(strlen(cp));
00204             bigEnough(length());
00205             strcpy(contents, cp);
00206         }
00207 }
00208 
00209 // Description:
00210 // Replaces the old contents of the current AString with the const
00211 // char argument \fIc\fP.
00212 void AString::copy(const char& c){
00213     length(1);
00214     bigEnough(length());
00215     contents[0] = c;
00216     contents[1] = '\0';
00217 }
00218 
00219 // Description:
00220 // Returns 1 if the variable \fIcontents\fP is equal to NULL and 0
00221 // otherwise.
00222 int AString::isNull() const {
00223     return(contents == NULL);
00224 }
00225 
00226 // public methods
00227 
00228 // Description:
00229 // Default constructor.
00230 AString::AString(){
00231     initVars();
00232 }
00233 
00234 // Description:
00235 // Converts a const char* into an AString.
00236 AString::AString(const char* cp){
00237     initVars();
00238     copy(cp);
00239 }
00240 
00241 // copy constructor
00242 AString::AString(const AString& as){
00243     initVars();
00244     copy(as);
00245 }
00246 
00247 AString::~AString(){
00248     delete contents;
00249 }
00250 
00251 // Description:
00252 // Returns the size of memory allocation hunks.
00253 int AString::chunksize() const {
00254     return(chunk_size > 0 ? chunk_size : default_chunk_size);
00255 }
00256 
00257 // Description:
00258 // Changes the size of memory allocation hunks.
00259 void AString::chunksize(const int new_size){
00260     if(new_size > 0)
00261         chunk_size = new_size;
00262 }
00263 
00264 // Description:
00265 // Returns 1 if the string is empty, 0 otherwise.
00266 int AString::empty() const {
00267     return (length() == 0);
00268 }
00269 
00270 // Description:
00271 // Returns the number of characters in the string.
00272 // Always non-negative.
00273 int AString::length() const{
00274     if(len == -1){
00275         AString* that = (AString*)(this); // cast away const-ness
00276         that->length(isNull() ? 0 : strlen(contents));
00277     }
00278     return(len);
00279 }
00280 
00281 // Description:
00282 // Assigns one AString to another. The user doesn't have to worry
00283 // about there being enough space to hold the new string.
00284 AString& AString::operator=(const AString& as){
00285     if(this != &as){                            // check for s = s
00286         delete contents;                        // zap the current guy
00287         initVars();
00288         chunksize(as.chunksize());
00289         copy(as);
00290     }
00291     return *this;
00292 }
00293 
00294 // Description:
00295 // Assigns a char* to an AString. The user doesn't have to worry
00296 // about there being enough space to hold the new string.
00297 AString& AString::operator=(const char* s){
00298     delete contents;                    // zap the current guy
00299     initVars();
00300     copy(s);
00301     return *this;
00302 }
00303 
00304 // Description:
00305 // Returns the (read-only) value of the \fIi\fPth character,
00306 // counting from zero.
00307 const char& AString::operator[](const long i) const{
00308     if(!inRange(i)){
00309         cerr << className() << "[" << i << "], i is out of range" << endl;
00310         exit(1);
00311     }
00312     return(contents[i]);
00313 }
00314 
00315 // Description:
00316 // Add an AString to the end of the current AString.
00317 AString& AString::operator+=(const AString& as){
00318     concat(as);
00319     return *this;
00320 }
00321 
00322 // Description:
00323 // Add a char* to the end of the current AString.
00324 AString& AString::operator+=(const char* s){
00325     concat(s);
00326     return *this;
00327 }
00328 
00329 // Description:
00330 // Return a (read-only) character pointer to the current AString.
00331 AString::operator const char*() const{
00332     if(isNull())
00333         return empty_string;
00334     else
00335         return(contents);
00336 }
00337 
00338 const char* AString::className() const{
00339     return(myNameIs);
00340 }
00341 
00342 // Description:
00343 // Return a lower-case'd version of the current AString.
00344 AString AString::asLowerCase() const
00345 {
00346     AString t = *this;
00347     for(int i = 0; i < len; i++)
00348         t.contents[i] = tolower(t.contents[i]);
00349     return t;
00350 }
00351 
00352 // friend functions
00353 
00354 // Description:
00355 // Return an AString formed by joining two AStrings.
00356 AString operator+(const AString& as, const AString& bs){
00357     AString tmp;
00358     tmp.bigEnough(as.length() + bs.length());
00359     tmp.concat(as);
00360     tmp.concat(bs);
00361     return tmp;
00362 }
00363 
00364 // Description:
00365 // Return an AString formed by joining an AString and a const char*.
00366 AString operator+(const AString& as, const char* s){
00367     AString tmp;
00368     tmp.bigEnough(as.length() + (s == NULL ? 0 : strlen(s)));
00369     tmp.concat(as);
00370     tmp.concat(s);
00371     return tmp;
00372 }
00373 
00374 // Description:
00375 // Return an AString formed by joining a const char* and an AString.
00376 AString operator+(const char* s, const AString& as){
00377     AString tmp;
00378     tmp.bigEnough((s == NULL ? 0 : strlen(s)) + as.length());
00379     tmp.concat(s);
00380     tmp.concat(as);
00381     return tmp;
00382 }
00383 
00384 // equality
00385 int operator==(const AString& as, const AString& bs){
00386     return(as.compare(bs) == 0);
00387 }
00388 
00389 int operator==(const AString& as, const char* s){
00390     return(as.compare(s) == 0);
00391 }
00392 
00393 int operator==(const char* s, const AString& as){
00394     return(as.compare(s) == 0);
00395 }
00396 
00397 // inequality
00398 int operator!=(const AString& as, const AString& bs){
00399     return(as.compare(bs) != 0);
00400 }
00401 
00402 int operator!=(const AString& as, const char* s){
00403     return(as.compare(s) != 0);
00404 }
00405 
00406 int operator!=(const char* s, const AString& as){
00407     return(as.compare(s) != 0);
00408 }
00409 
00410 // greater than
00411 int operator>(const AString& as, const AString& bs){
00412     return(as.compare(bs) > 0);
00413 }
00414 
00415 int operator>(const AString& as, const char* s){
00416     return(as.compare(s) > 0);
00417 }
00418 
00419 int operator>(const char* s, const AString& as){
00420     return(as.compare(s) < 0);  // reverse the order 
00421 }
00422 
00423 // greater than or equal to
00424 int operator>=(const AString& as, const AString& bs){
00425     return(as.compare(bs) >= 0);
00426 }
00427 
00428 int operator>=(const AString& as, const char* s){
00429     return(as.compare(s) >= 0);
00430 }
00431 
00432 int operator>=(const char* s, const AString& as){
00433     return(as.compare(s) <= 0); // reverse the order
00434 }
00435 
00436 // less than
00437 int operator<(const AString& as, const AString& bs){
00438     return(as.compare(bs) < 0);
00439 }
00440 
00441 int operator<(const AString& as, const char* s){
00442     return(as.compare(s) < 0);
00443 }
00444 
00445 int operator<(const char* s, const AString& as){
00446     return(as.compare(s) > 0);  // reverse the order
00447 }
00448 
00449 // less than or equal to
00450 int operator<=(const AString& as, const AString& bs){
00451     return(as.compare(bs) <= 0);
00452 }
00453 
00454 int operator<=(const AString& as, const char* s){
00455     return(as.compare(s) <= 0);
00456 }
00457 
00458 int operator<=(const char* s, const AString& as){
00459     return(as.compare(s) >= 0); // reverse the order
00460 }
00461 
00462 ostream& operator<<(ostream& fp, const AString& as)
00463 {
00464    fp << as.contents;
00465 
00466    return fp;
00467 }
00468 
00469 istream& operator>>(istream& fp, AString& as)
00470 {
00471    fp >> as.contents;
00472 
00473    return fp;
00474 }
00475 
00476 
00477 // functions
00478 
00479 #include <stdarg.h>             // to get varargs
00480 
00481 // Description:
00482 // Format, according to \fIfmt\fP the arguments to ASFormat() and
00483 // into an AString.  Uses printf(3) style arguments.
00484 AString ASFormat(char* fmt, ...){
00485     va_list     arg_list;
00486     char        s[1024];
00487     
00488     va_start(arg_list, fmt);
00489     (void) vsprintf(s, fmt, arg_list);
00490     va_end(arg_list);
00491 
00492     AString as = s;
00493     return as;
00494 }
00495 
00496 // Description:
00497 // Convert an unsigned char into an AString.
00498 AString toAS(unsigned char uc){
00499     return ASFormat("%c", uc);
00500 }
00501 
00502 // Description:
00503 // Convert a char into an AString.
00504 AString toAS(char c){
00505     return ASFormat("%c", c);
00506 }
00507 
00508 // Description:
00509 // Convert an unsigned short into its AString representation.
00510 AString toAS(unsigned short um){
00511     return ASFormat("%hu", um);
00512 }
00513 
00514 // Description:
00515 // Convert a short into its AString representation.
00516 AString toAS(short m){
00517     return ASFormat("%hd", m);
00518 }
00519 
00520 // Description:
00521 // Convert a unsigned int into its AString representation.
00522 AString toAS(unsigned int um){
00523     return ASFormat("%u", um);
00524 }
00525 
00526 // Description:
00527 // Convert a int into its AString representation.
00528 AString toAS(int m){
00529     return ASFormat("%d", m);
00530 }
00531 
00532 // Description:
00533 // Convert a long into its AString representation.
00534 AString toAS(unsigned long um){
00535     return ASFormat("%lu", um);
00536 }
00537 
00538 // Description:
00539 // Convert a long into its AString representation.
00540 AString toAS(long m){
00541     return ASFormat("%d", m);
00542 }
00543 
00544 // Description:
00545 // Convert a float or float into its AString representation.
00546 AString toAS(double d){
00547     return ASFormat("%g", d);
00548 }
00549  
00550 }

Generated on Wed Dec 15 21:20:27 2004 for vuVolume by  doxygen 1.3.9.1