libpniio
string_sequence_rule.hpp
Go to the documentation of this file.
1 // (c) Copyright 2015 DESY, Eugen Wintersberger <eugen.wintersberger@desy.de>
2 //
3 // This file is part of libpniio.
4 //
5 // libpniio is free software: you can redistribute it and/or modify
6 // it under the terms of the GNU General Public License as published by
7 // the Free Software Foundation, either version 2 of the License, or
8 // (at your option) any later version.
9 //
10 // libpniio is distributed in the hope that it will be useful,
11 // but WITHOUT ANY WARRANTY; without even the implied warranty of
12 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13 // GNU General Public License for more details.
14 //
15 // You should have received a copy of the GNU General Public License
16 // along with libpniio. If not, see <http://www.gnu.org/licenses/>.
17 // ===========================================================================
18 //
19 // Created on: Feb 2, 2015
20 // Author: Eugen Wintersberger <eugen.wintersberger@desy.de>
21 //
22 //
23 #pragma once
24 
25 
26 #include <sstream>
27 
28 #include <boost/algorithm/string.hpp>
29 #include <boost/spirit/include/phoenix.hpp>
30 #include<pni/core/types.hpp>
31 #include<pni/core/error.hpp>
32 #include<vector>
33 
34 #include "../exceptions.hpp"
35 #include "get_rule_type.hpp"
36 #include "delimiter_rule.hpp"
37 
38 namespace pni{
39 namespace io{
40 
48  struct trim_string
49  {
53  template<typename Sig> struct result
54  {
55  typedef pni::core::string type;
56  };
57 
58  //--------------------------------------------------------------------
69  template<typename Arg>
70  pni::core::string operator()(Arg const &n) const
71  {
72  pni::core::string output(n.begin(),n.end());
73  boost::trim(output);
74  return output;
75  }
76  };
77 
78 
79  //------------------------------------------------------------------------
98  template<
99  typename ITERT,
100  typename ST
101  >
102  struct string_sequence_rule : boost::spirit::qi::grammar<ITERT,ST()>
103  {
105  boost::spirit::qi::rule<ITERT,pni::core::string()> element_rule_;
107  boost::spirit::qi::rule<ITERT> start_;
109  boost::spirit::qi::rule<ITERT> stop_;
111  boost::spirit::qi::rule<ITERT> delimiter_;
112 
114  boost::spirit::qi::rule<ITERT,ST()> sequence_;
115 
117  boost::phoenix::function<trim_string> trim;
118 
119  //--------------------------------------------------------------------
127  string_sequence_rule() : string_sequence_rule::base_type(sequence_)
128  {
129  using namespace boost::spirit;
130  using qi::_val;
131  using qi::_1;
132 
133  delimiter_ = +qi::blank;
134  element_rule_ = (*(qi::char_-delimiter_))[_val = trim(_1)];
135  sequence_ = element_rule_ % delimiter_;
136  }
137 
138  //--------------------------------------------------------------------
150  string_sequence_rule::base_type(sequence_)
151  {
152  using namespace boost::spirit;
153  using qi::_val;
154  using qi::_1;
155 
156  if(del==' ')
157  delimiter_ = +qi::blank;
158  else
159  delimiter_ = qi::char_(del);
160 
161  element_rule_ = (*(qi::char_-delimiter_))[_val = trim(_1)];
162  sequence_ = element_rule_ % delimiter_;
163  }
164 
165  //--------------------------------------------------------------------
177  string_sequence_rule(char start,char stop):
178  string_sequence_rule::base_type(sequence_)
179  {
180  using namespace boost::spirit;
181  using qi::_1;
182  using qi::_val;
183 
184  start_ = qi::char_(start)>*qi::blank;
185  stop_ = *qi::blank>qi::char_(stop);
186  delimiter_ = +qi::blank;
187  element_rule_ = (+(qi::char_-(qi::lit(stop)|qi::blank)))[_val=trim(_1)];
188  sequence_ = start_> (element_rule_ % delimiter_)>stop_;
189  }
190 
191  //--------------------------------------------------------------------
202  string_sequence_rule(char start,char stop,char del):
203  string_sequence_rule::base_type(sequence_)
204  {
205  using namespace boost::spirit;
206  start_ = qi::char_(start)>*qi::blank;
207  stop_ = *qi::blank>qi::char_(stop);
208 
209  if(del==' ')
210  delimiter_ = +qi::blank;
211  else
212  delimiter_ = qi::char_(del);
213 
214  element_rule_ = (*(qi::char_-(qi::lit(stop)|delimiter_)))[qi::_val =
215  trim(qi::_1)];
216  sequence_ = start_>(element_rule_ % delimiter_)>stop_;
217  }
218 
219  };
220 
221 //end of namespace
222 }
223 }
string_sequence_rule(char del)
constructor
Definition: string_sequence_rule.hpp:149
boost::spirit::qi::rule< ITERT > delimiter_
rule for the delimiter symbol for the sequence
Definition: string_sequence_rule.hpp:111
boost::spirit::qi::rule< ITERT > stop_
rule for the stop symbol for the sequence
Definition: string_sequence_rule.hpp:109
boost::phoenix::function< trim_string > trim
lazy function to trim the read string
Definition: string_sequence_rule.hpp:117
string_sequence_rule()
default constructor
Definition: string_sequence_rule.hpp:127
container parser
Definition: string_sequence_rule.hpp:102
Definition: spirit_container_traits.hpp:33
Definition: cbf_reader.hpp:41
boost::spirit::qi::rule< ITERT, ST()> sequence_
the full rule to parse the sequence
Definition: string_sequence_rule.hpp:114
return type of the lazy function
Definition: string_sequence_rule.hpp:53
lazy string trimming
Definition: string_sequence_rule.hpp:48
string_sequence_rule(char start, char stop, char del)
constructor
Definition: string_sequence_rule.hpp:202
boost::spirit::qi::rule< ITERT, pni::core::string()> element_rule_
rule to parse a single element of the sequence
Definition: string_sequence_rule.hpp:105
boost::spirit::qi::rule< ITERT > start_
rule for the start symbol of the sequence
Definition: string_sequence_rule.hpp:107
string_sequence_rule(char start, char stop)
constructor
Definition: string_sequence_rule.hpp:177
pni::core::string operator()(Arg const &n) const
trim implementation
Definition: string_sequence_rule.hpp:70
pni::core::string type
return value
Definition: string_sequence_rule.hpp:55