stringclass.h revision 75584
1// -*- C++ -*-
2/* Copyright (C) 1989, 1990, 1991, 1992 Free Software Foundation, Inc.
3     Written by James Clark (jjc@jclark.com)
4
5This file is part of groff.
6
7groff is free software; you can redistribute it and/or modify it under
8the terms of the GNU General Public License as published by the Free
9Software Foundation; either version 2, or (at your option) any later
10version.
11
12groff is distributed in the hope that it will be useful, but WITHOUT ANY
13WARRANTY; without even the implied warranty of MERCHANTABILITY or
14FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
15for more details.
16
17You should have received a copy of the GNU General Public License along
18with groff; see the file COPYING.  If not, write to the Free Software
19Foundation, 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. */
20
21#include <string.h>
22#include <stdio.h>
23#include <assert.h>
24
25// Ensure that the first declaration of functions that are later
26// declared as inline declares them as inline.
27
28class string;
29
30inline string operator+(const string &, const string &);
31inline string operator+(const string &, const char *);
32inline string operator+(const char *, const string &);
33inline string operator+(const string &, char);
34inline string operator+(char, const string &);
35inline int operator==(const string &, const string &);
36inline int operator!=(const string &, const string &);
37
38class string {
39public:
40  string();
41  string(const string &);
42  string(const char *);
43  string(const char *, int);
44  string(char);
45
46  ~string();
47
48  string &operator=(const string &);
49  string &operator=(const char *);
50  string &operator=(char);
51
52  string &operator+=(const string &);
53  string &operator+=(const char *);
54  string &operator+=(char);
55  void append(const char *, int);
56
57  int length() const;
58  int empty() const;
59  int operator*() const;
60
61  string substring(int i, int n) const;
62
63  char &operator[](int);
64  char operator[](int) const;
65
66  void set_length(int i);
67  const char *contents() const;
68  int search(char) const;
69  char *extract() const;
70  void clear();
71  void move(string &);
72
73  friend string operator+(const string &, const string &);
74  friend string operator+(const string &, const char *);
75  friend string operator+(const char *, const string &);
76  friend string operator+(const string &, char);
77  friend string operator+(char, const string &);
78
79  friend int operator==(const string &, const string &);
80  friend int operator!=(const string &, const string &);
81  friend int operator<=(const string &, const string &);
82  friend int operator<(const string &, const string &);
83  friend int operator>=(const string &, const string &);
84  friend int operator>(const string &, const string &);
85
86private:
87  char *ptr;
88  int len;
89  int sz;
90
91  string(const char *, int, const char *, int);	// for use by operator+
92  void grow1();
93};
94
95
96inline char &string::operator[](int i)
97{
98  assert(i >= 0 && i < len);
99  return ptr[i];
100}
101
102inline char string::operator[](int i) const
103{
104  assert(i >= 0 && i < len);
105  return ptr[i];
106}
107
108inline int string::length() const
109{
110  return len;
111}
112
113inline int string::empty() const
114{
115  return len == 0;
116}
117
118inline int string::operator*() const
119{
120  return len;
121}
122
123inline const char *string::contents() const
124{
125  return  ptr;
126}
127
128inline string operator+(const string &s1, const string &s2)
129{
130  return string(s1.ptr, s1.len, s2.ptr, s2.len);
131}
132
133inline string operator+(const string &s1, const char *s2)
134{
135#ifdef __GNUG__
136  if (s2 == 0)
137    return s1;
138  else
139    return string(s1.ptr, s1.len, s2, strlen(s2));
140#else
141  return s2 == 0 ? s1 : string(s1.ptr, s1.len, s2, strlen(s2));
142#endif
143}
144
145inline string operator+(const char *s1, const string &s2)
146{
147#ifdef __GNUG__
148  if (s1 == 0)
149    return s2;
150  else
151    return string(s1, strlen(s1), s2.ptr, s2.len);
152#else
153  return s1 == 0 ? s2 : string(s1, strlen(s1), s2.ptr, s2.len);
154#endif
155}
156
157inline string operator+(const string &s, char c)
158{
159  return string(s.ptr, s.len, &c, 1);
160}
161
162inline string operator+(char c, const string &s)
163{
164  return string(&c, 1, s.ptr, s.len);
165}
166
167inline int operator==(const string &s1, const string &s2)
168{
169  return (s1.len == s2.len
170	  && (s1.len == 0 || memcmp(s1.ptr, s2.ptr, s1.len) == 0));
171}
172
173inline int operator!=(const string &s1, const string &s2)
174{
175  return (s1.len != s2.len
176	  || (s1.len != 0 && memcmp(s1.ptr, s2.ptr, s1.len) != 0));
177}
178
179inline string string::substring(int i, int n) const
180{
181  assert(i >= 0 && i + n <= len);
182  return string(ptr + i, n);
183}
184
185inline string &string::operator+=(char c)
186{
187  if (len >= sz)
188    grow1();
189  ptr[len++] = c;
190  return *this;
191}
192
193void put_string(const string &, FILE *);
194
195string as_string(int);
196