Line data Source code
1 : /****************************************************************************/
2 : // Eclipse SUMO, Simulation of Urban MObility; see https://eclipse.dev/sumo
3 : // Copyright (C) 2001-2024 German Aerospace Center (DLR) and others.
4 : // This program and the accompanying materials are made available under the
5 : // terms of the Eclipse Public License 2.0 which is available at
6 : // https://www.eclipse.org/legal/epl-2.0/
7 : // This Source Code may also be made available under the following Secondary
8 : // Licenses when the conditions for such availability set forth in the Eclipse
9 : // Public License 2.0 are satisfied: GNU General Public License, version 2
10 : // or later which is available at
11 : // https://www.gnu.org/licenses/old-licenses/gpl-2.0-standalone.html
12 : // SPDX-License-Identifier: EPL-2.0 OR GPL-2.0-or-later
13 : /****************************************************************************/
14 : /// @file StringTokenizer.cpp
15 : /// @author Daniel Krajzewicz
16 : /// @author Jakob Erdmann
17 : /// @author Michael Behrisch
18 : /// @date ?
19 : ///
20 : // A java-style StringTokenizer for c++ (stl)
21 : /****************************************************************************/
22 : #include <config.h>
23 :
24 : #include <string>
25 : #include <vector>
26 : #include <iostream> // !!! debug only
27 :
28 : #include "UtilExceptions.h"
29 : #include "StringTokenizer.h"
30 :
31 :
32 : // ===========================================================================
33 : // variable definitions
34 : // ===========================================================================
35 : const int StringTokenizer::NEWLINE = -256;
36 : const int StringTokenizer::WHITECHARS = -257;
37 : const int StringTokenizer::SPACE = 32;
38 : const int StringTokenizer::TAB = 9;
39 :
40 :
41 : // ===========================================================================
42 : // method definitions
43 : // ===========================================================================
44 :
45 119 : StringTokenizer::StringTokenizer() :
46 119 : myPos(0) {
47 119 : }
48 :
49 :
50 4701910 : StringTokenizer::StringTokenizer(std::string tosplit) :
51 4701910 : myTosplit(tosplit), myPos(0) {
52 4701910 : prepareWhitechar(tosplit);
53 4701910 : }
54 :
55 :
56 16674367 : StringTokenizer::StringTokenizer(std::string tosplit, std::string token, bool splitAtAllChars) :
57 16674367 : myTosplit(tosplit), myPos(0) {
58 16674367 : prepare(tosplit, token, splitAtAllChars);
59 16674367 : }
60 :
61 :
62 2494 : StringTokenizer::StringTokenizer(std::string tosplit, int special) :
63 2494 : myTosplit(tosplit), myPos(0) {
64 2494 : switch (special) {
65 : case NEWLINE:
66 1 : prepare(tosplit, "\r\n", true);
67 1 : break;
68 : case TAB:
69 679 : prepare(tosplit, "\t", true);
70 679 : break;
71 1321 : case WHITECHARS:
72 1321 : prepareWhitechar(tosplit);
73 : break;
74 493 : default:
75 493 : char* buf = new char[2];
76 493 : buf[0] = (char) special;
77 493 : buf[1] = 0;
78 493 : prepare(tosplit, buf, false);
79 493 : delete[] buf;
80 : break;
81 : }
82 2494 : }
83 :
84 :
85 21378890 : StringTokenizer::~StringTokenizer() {}
86 :
87 :
88 2972936 : void StringTokenizer::reinit() {
89 2972936 : myPos = 0;
90 2972936 : }
91 :
92 :
93 34353761 : bool StringTokenizer::hasNext() {
94 34353761 : return myPos != (int)myStarts.size();
95 : }
96 :
97 :
98 49869972 : std::string StringTokenizer::next() {
99 49869972 : if (myPos >= (int)myStarts.size()) {
100 8 : throw OutOfBoundsException();
101 : }
102 49869968 : if (myLengths[myPos] == 0) {
103 77 : myPos++;
104 77 : return "";
105 : }
106 49869891 : int start = myStarts[myPos];
107 49869891 : int length = myLengths[myPos++];
108 49869891 : return myTosplit.substr(start, length);
109 : }
110 :
111 :
112 880 : std::string StringTokenizer::front() {
113 880 : if (myStarts.size() == 0) {
114 0 : throw OutOfBoundsException();
115 : }
116 880 : if (myLengths[0] == 0) {
117 0 : return "";
118 : }
119 880 : return myTosplit.substr(myStarts[0], myLengths[0]);
120 : }
121 :
122 :
123 263069 : std::string StringTokenizer::get(int pos) const {
124 263069 : if (pos >= (int)myStarts.size()) {
125 4 : throw OutOfBoundsException();
126 : }
127 263067 : if (myLengths[pos] == 0) {
128 574 : return "";
129 : }
130 262493 : int start = myStarts[pos];
131 : int length = myLengths[pos];
132 262493 : return myTosplit.substr(start, length);
133 : }
134 :
135 :
136 26667878 : int StringTokenizer::size() const {
137 26667878 : return (int)myStarts.size();
138 : }
139 :
140 :
141 16675540 : void StringTokenizer::prepare(const std::string& tosplit, const std::string& token, bool splitAtAllChars) {
142 16675540 : int beg = 0;
143 16675540 : int len = (int)token.length();
144 16675540 : if (splitAtAllChars) {
145 : len = 1;
146 : }
147 53106843 : while (beg < (int)tosplit.length()) {
148 : std::string::size_type end;
149 36431303 : if (splitAtAllChars) {
150 11521 : end = tosplit.find_first_of(token, beg);
151 : } else {
152 36419782 : end = tosplit.find(token, beg);
153 : }
154 36431303 : if (end == std::string::npos) {
155 : end = tosplit.length();
156 : }
157 36431303 : myStarts.push_back(beg);
158 36431303 : myLengths.push_back((int)end - beg);
159 36431303 : beg = (int)end + len;
160 36431303 : if (beg == (int)tosplit.length()) {
161 40 : myStarts.push_back(beg - 1);
162 40 : myLengths.push_back(0);
163 : }
164 : }
165 16675540 : }
166 :
167 :
168 4703231 : void StringTokenizer::prepareWhitechar(const std::string& tosplit) {
169 : std::string::size_type len = tosplit.length();
170 : std::string::size_type beg = 0;
171 4703325 : while (beg < len && tosplit[beg] <= SPACE) {
172 94 : beg++;
173 : }
174 19664279 : while (beg != std::string::npos && beg < len) {
175 : std::string::size_type end = beg;
176 176676017 : while (end < len && tosplit[end] > SPACE) {
177 161714969 : end++;
178 : }
179 14961048 : myStarts.push_back((int)beg);
180 14961048 : myLengths.push_back((int)end - (int)beg);
181 : beg = end;
182 25686757 : while (beg < len && tosplit[beg] <= SPACE) {
183 10725709 : beg++;
184 : }
185 : }
186 4703231 : }
187 :
188 :
189 : std::vector<std::string>
190 2972935 : StringTokenizer::getVector() {
191 : std::vector<std::string> ret;
192 2972935 : ret.reserve(size());
193 9963065 : while (hasNext()) {
194 13980260 : ret.push_back(next());
195 : }
196 2972935 : reinit();
197 2972935 : return ret;
198 0 : }
199 :
200 :
201 : std::set<std::string>
202 28 : StringTokenizer::getSet() {
203 28 : std::vector<std::string> v = getVector();
204 56 : return std::set<std::string>(v.begin(), v.end());
205 28 : }
206 :
207 :
208 : /****************************************************************************/
|