Planet
navi homePPSaboutscreenshotsdownloaddevelopmentforum

source: orxonox.OLD/branches/std/src/lib/util/substring.cc @ 7212

Last change on this file since 7212 was 7212, checked in by bensch, 18 years ago

should be better, but hey…. its late

File size: 6.5 KB
RevLine 
[4597]1/*
[3941]2   orxonox - the future of 3D-vertical-scrollers
3
4   Copyright (C) 2004 orx
5
6   This program is free software; you can redistribute it and/or modify
7   it under the terms of the GNU General Public License as published by
8   the Free Software Foundation; either version 2, or (at your option)
9   any later version.
10
11   ### File Specific:
12   main-programmer: Christian Meyer
[4597]13   co-programmer: Benjamin Grauer
14
15   2005-06-10: some naming conventions
[7212]16
17//
18//  splitLine
19//  STL string tokenizer
20//
21//  Created by Clemens Wacha.
22//  Version 1.0
23//  Copyright (c) 2005 Clemens Wacha. All rights reserved.
24//
25
[4220]26*/
27
28
[3941]29/**
[4836]30 *  breaks a string into parts that were initially seperated by comma
31 * @param string the string to break into substrings
[4220]32*/
[3941]33
[4220]34#include "substring.h"
35
36#include <string.h>
[7211]37#include <cassert>
[4220]38
[7211]39SubString::SubString(const std::string& string, char splitter)
[4220]40{
[7211]41  char split[2];
42  split[0] = splitter;
43  split[1] = '\0';
44  SubString::splitLine(this->strings, this->offsets,
45                       string, split);
[4220]46}
47
[3941]48/**
[5183]49 * Splits a String into a Substring removing all whiteSpaces
50 * @param string the String to Split
51 * @param whiteSpaces MUST BE __TRUE__
52 *
53 */
[7211]54SubString::SubString(const std::string& string, bool whiteSpaces)
[5183]55{
[7211]56  SubString::splitLine(this->strings, this->offsets,
57                      string);
58}
59SubString::SubString(const std::string& string, const std::string& splitters, char escapeChar,char safemode_char, char comment_char)
60{
61  SubString::splitLine(this->strings, this->offsets,
62                       string, splitters, escapeChar, safemode_char);
63}
[5183]64
65
[7212]66unsigned int SubString::split(const std::string& string, char splitter)
67{
68  this->offsets.clear();
69  this->strings.clear();
70  char split[2];
71  split[0] = splitter;
72  split[1] = '\0';
73  SubString::splitLine(this->strings, this->offsets, string, split);
74  return strings.size();
75}
76
77
[7211]78/**
[7212]79 * Splits a String into a Substring removing all whiteSpaces
80 * @param string the String to Split
81 * @param whiteSpaces MUST BE __TRUE__
82 *
83 */
84unsigned int SubString::split(const std::string& string, bool whiteSpaces)
85{
86  this->offsets.clear();
87  this->strings.clear();
88  SubString::splitLine(this->strings, this->offsets, string);
89  return strings.size();
90}
91
92unsigned int SubString::split(const std::string& string, const std::string& splitters, char escapeChar,char safemode_char, char comment_char)
93{
94  this->offsets.clear();
95  this->strings.clear();
96  SubString::splitLine(this->strings, this->offsets,
97                       string, splitters, escapeChar, safemode_char);
98  return strings.size();
99}
100
101
102/**
[7211]103 * splits line into tokens and stores them in ret. Supports delimiters, escape characters,
104 * ignores special  characters between safemode_char and between comment_char and linend '\n'.
105 *
106 * @returns SPLIT_LINE_STATE the parser was in when returning
107 */
108SPLIT_LINE_STATE SubString::splitLine(std::vector<std::string>& ret, std::vector<unsigned int>& offsets,
109                                      const std::string& line, const std::string& delimiters,
110                                      char escape_char, char safemode_char, char comment_char,
111                                      SPLIT_LINE_STATE start_state)
112{
113  SPLIT_LINE_STATE state = start_state;
[5183]114  unsigned int i = 0;
[7211]115  std::string token;
[5183]116
[7211]117  if(start_state != SL_NORMAL && ret.size() > 0)
[5656]118  {
[7211]119    token = ret[ret.size()-1];
120    ret.pop_back();
[5656]121  }
122
[7211]123  while(i < line.size())
[5656]124  {
[7211]125    switch(state)
[5656]126    {
[7211]127    case SL_NORMAL:
128      if(line[i] == escape_char)
[5656]129      {
[7211]130        state = SL_ESCAPE;
[5656]131      }
[7211]132      else if(line[i] == safemode_char)
133      {
134        state = SL_SAFEMODE;
135      }
136      else if(line[i] == comment_char)
137      {
138        /// FINISH
139        if(token.size() > 0)
140        {
141          ret.push_back(token);
142          offsets.push_back(i);
143          token.clear();
144        }
145        token += line[i];       // EAT
146        state = SL_COMMENT;
147      }
148      else if(delimiters.find(line[i]) != std::string::npos)
149      {
150        // line[i] is a delimiter
151        /// FINISH
152        if(token.size() > 0)
153        {
154          ret.push_back(token);
155          offsets.push_back(i);
156          token.clear();
157        }
158      }
159      else
160      {
161        token += line[i];       // EAT
162      }
163      break;
164    case SL_ESCAPE:
165      if(line[i] == 'n') token += '\n';
166      else if(line[i] == 't') token += '\t';
167      else if(line[i] == 'v') token += '\v';
168      else if(line[i] == 'b') token += '\b';
169      else if(line[i] == 'r') token += '\r';
170      else if(line[i] == 'f') token += '\f';
171      else if(line[i] == 'a') token += '\a';
172      else if(line[i] == '?') token += '\?';
173      else token += line[i];  // EAT
174      state = SL_NORMAL;
175      break;
176    case SL_SAFEMODE:
177      if(line[i] == safemode_char)
178      {
179        state = SL_NORMAL;
180      }
181      else if(line[i] == escape_char)
182      {
183        state = SL_SAFEESCAPE;
184      }
185      else
186      {
187        token += line[i];       // EAT
188      }
189      break;
190    case SL_SAFEESCAPE:
191      if(line[i] == 'n') token += '\n';
192      else if(line[i] == 't') token += '\t';
193      else if(line[i] == 'v') token += '\v';
194      else if(line[i] == 'b') token += '\b';
195      else if(line[i] == 'r') token += '\r';
196      else if(line[i] == 'f') token += '\f';
197      else if(line[i] == 'a') token += '\a';
198      else if(line[i] == '?') token += '\?';
199      else token += line[i];  // EAT
200      state = SL_SAFEMODE;
201      break;
202    case SL_COMMENT:
203      if(line[i] == '\n')
204      {
205        /// FINISH
206        if(token.size() > 0)
207        {
208          ret.push_back(token);
209          offsets.push_back(i);
210          token.clear();
211        }
212        state = SL_NORMAL;
213      }
214      else
215      {
216        token += line[i];       // EAT
217      }
218      break;
219    default:
220      // nothing
221      break;
[5656]222    }
[7211]223    i++;
[5656]224  }
225
[7211]226  /// FINISH
227  if(token.size() > 0)
[5656]228  {
[7211]229    ret.push_back(token);
230    offsets.push_back(i);
231    token.clear();
[5656]232  }
[7211]233  return(state);
[5656]234}
235
[5183]236/**
[4836]237 *  removes the object from memory
[3941]238*/
[4220]239SubString::~SubString()
[7211]240{ }
[3941]241
242/**
[5200]243 * get a particular substring's offset
244 * @param i the ID of the substring to get the offset from
245 * @returns the offset or NULL if an invalid ID was given
246 */
247unsigned int SubString::getOffset(unsigned int i)
248{
[7211]249  if( i < this->offsets.size() && i >= 0)
[5200]250    return this->offsets[i];
251  else
252    return 0;
253}
254
255/**
[4833]256 * Some nice debug information about this SubString
257 */
258void SubString::debug() const
259{
[7211]260  printf("Substring-information::count=%d ::", this->strings.size());
261  for (unsigned int i = 0; i < this->strings.size(); i++)
262    printf("s%d='%s'::", i, this->strings[i].c_str());
263  printf("\n");
[4833]264}
Note: See TracBrowser for help on using the repository browser.