yat/utility/getvector.h

Code
Comments
Other
Rev Date Author Line
3639 26 Apr 17 peter 1 #ifndef _theplu_yat_utility_getvector_
3639 26 Apr 17 peter 2 #define _theplu_yat_utility_getvector_
3639 26 Apr 17 peter 3
3639 26 Apr 17 peter 4 // $Id$
3639 26 Apr 17 peter 5
3639 26 Apr 17 peter 6 /*
4207 26 Aug 22 peter 7   Copyright (C) 2017, 2020, 2021, 2022 Peter Johansson
3639 26 Apr 17 peter 8
3639 26 Apr 17 peter 9   This file is part of the yat library, http://dev.thep.lu.se/yat
3639 26 Apr 17 peter 10
3639 26 Apr 17 peter 11   The yat library is free software; you can redistribute it and/or
3639 26 Apr 17 peter 12   modify it under the terms of the GNU General Public License as
3639 26 Apr 17 peter 13   published by the Free Software Foundation; either version 3 of the
3639 26 Apr 17 peter 14   License, or (at your option) any later version.
3639 26 Apr 17 peter 15
3639 26 Apr 17 peter 16   The yat library is distributed in the hope that it will be useful,
3639 26 Apr 17 peter 17   but WITHOUT ANY WARRANTY; without even the implied warranty of
3639 26 Apr 17 peter 18   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
3639 26 Apr 17 peter 19   General Public License for more details.
3639 26 Apr 17 peter 20
3639 26 Apr 17 peter 21   You should have received a copy of the GNU General Public License
3639 26 Apr 17 peter 22   along with yat. If not, see <http://www.gnu.org/licenses/>.
3639 26 Apr 17 peter 23 */
3639 26 Apr 17 peter 24
3639 26 Apr 17 peter 25 #include <yat/utility/split.h>
3639 26 Apr 17 peter 26 #include <yat/utility/utility.h>
3639 26 Apr 17 peter 27
4195 12 Aug 22 peter 28 #include <boost/algorithm/string/classification.hpp>
3639 26 Apr 17 peter 29 #include <boost/type_traits/is_same.hpp>
3639 26 Apr 17 peter 30
3639 26 Apr 17 peter 31 #include <istream>
3639 26 Apr 17 peter 32 #include <string>
4096 16 Sep 21 peter 33 #include <utility>
3639 26 Apr 17 peter 34 #include <vector>
3639 26 Apr 17 peter 35
3639 26 Apr 17 peter 36 namespace theplu {
3639 26 Apr 17 peter 37 namespace yat {
3639 26 Apr 17 peter 38 namespace utility {
3639 26 Apr 17 peter 39
3639 26 Apr 17 peter 40   /**
3639 26 Apr 17 peter 41      Read all elements is \a is until \a newlinedelim or end of
3639 26 Apr 17 peter 42      stream. Elements seprated by \a delim are split and push_backed
3639 26 Apr 17 peter 43      in result. If \c T is not \c std::string, elements are converted
3639 26 Apr 17 peter 44      to \c T using \c convert<T>.
3639 26 Apr 17 peter 45
3639 26 Apr 17 peter 46      \see convert<T>(const std::string&)
3639 26 Apr 17 peter 47      \see split(std::string, const std::string&, char delim)
3639 26 Apr 17 peter 48
3639 26 Apr 17 peter 49      \since New in yat 0.15
3639 26 Apr 17 peter 50
3639 26 Apr 17 peter 51      \return \a is
3639 26 Apr 17 peter 52    */
3639 26 Apr 17 peter 53   template<typename T>
3639 26 Apr 17 peter 54   std::istream& getvector(std::istream& is, std::vector<T>& result,
3639 26 Apr 17 peter 55                           char delim, char newlinedelim='\n');
3639 26 Apr 17 peter 56
3639 26 Apr 17 peter 57   /**
3639 26 Apr 17 peter 58      Same as getvector(std::istream&, std::vector<T>&, char, char) but
3639 26 Apr 17 peter 59      elements are delimited with either character in delim.
3639 26 Apr 17 peter 60
3639 26 Apr 17 peter 61      \since New in yat 0.15
3639 26 Apr 17 peter 62    */
3639 26 Apr 17 peter 63   template<typename T>
3639 26 Apr 17 peter 64   std::istream& getvector(std::istream& is, std::vector<T>& result,
3639 26 Apr 17 peter 65                           const std::string& delim, char newlinedelim='\n');
3639 26 Apr 17 peter 66
3639 26 Apr 17 peter 67
3639 26 Apr 17 peter 68   // private stuff
3639 26 Apr 17 peter 69   namespace detail {
3639 26 Apr 17 peter 70
3639 26 Apr 17 peter 71     template<typename T>
4096 16 Sep 21 peter 72     void convert(std::vector<std::string>&& vec,
3639 26 Apr 17 peter 73                  std::vector<T>& result, boost::true_type is_string)
3639 26 Apr 17 peter 74     {
4096 16 Sep 21 peter 75       result = std::move(vec);
3639 26 Apr 17 peter 76     }
3639 26 Apr 17 peter 77
3639 26 Apr 17 peter 78
3639 26 Apr 17 peter 79     template<typename T>
4096 16 Sep 21 peter 80     void convert(const std::vector<std::string>& vec,
3639 26 Apr 17 peter 81                  std::vector<T>& result, boost::false_type is_string)
3639 26 Apr 17 peter 82     {
3930 08 Jul 20 peter 83       result.clear();
3639 26 Apr 17 peter 84       result.reserve(vec.size());
4194 12 Aug 22 peter 85       for (const std::string& v : vec)
4194 12 Aug 22 peter 86         result.push_back(utility::convert<T>(v));
3639 26 Apr 17 peter 87     }
3639 26 Apr 17 peter 88
3639 26 Apr 17 peter 89
3639 26 Apr 17 peter 90     /**
3639 26 Apr 17 peter 91        DELIM is char or const std::string&
3639 26 Apr 17 peter 92      */
4195 12 Aug 22 peter 93     template<typename Predicate, typename T>
3639 26 Apr 17 peter 94     std::istream& getvector(std::istream& is, std::vector<T>& result,
4195 12 Aug 22 peter 95                             Predicate pred, char delim)
3639 26 Apr 17 peter 96     {
4195 12 Aug 22 peter 97       if (is.good() == false)
3639 26 Apr 17 peter 98         return is;
3639 26 Apr 17 peter 99       std::vector<std::string> vec;
4195 12 Aug 22 peter 100       char c;
4195 12 Aug 22 peter 101       std::string word;
4195 12 Aug 22 peter 102       while (is.get(c)) {
4195 12 Aug 22 peter 103         if (pred(c)) {
4195 12 Aug 22 peter 104           vec.push_back(std::move(word));
4195 12 Aug 22 peter 105           word = "";
4195 12 Aug 22 peter 106         }
4195 12 Aug 22 peter 107         else if (c == delim)
4195 12 Aug 22 peter 108           break;
4195 12 Aug 22 peter 109         else
4195 12 Aug 22 peter 110           word += c;
4195 12 Aug 22 peter 111       }
4195 12 Aug 22 peter 112       // if is contained no characters, not even delim, leave result empty
4195 12 Aug 22 peter 113       if (vec.empty() && word=="" && is.good()==false)
4195 12 Aug 22 peter 114         return is;
4195 12 Aug 22 peter 115       vec.push_back(std::move(word));
4195 12 Aug 22 peter 116
3639 26 Apr 17 peter 117       typename boost::is_same<T, std::string> is_string;
4096 16 Sep 21 peter 118       convert(std::move(vec), result, is_string);
3639 26 Apr 17 peter 119       return is;
3639 26 Apr 17 peter 120     }
3639 26 Apr 17 peter 121
3639 26 Apr 17 peter 122   } // end namespace detail
3639 26 Apr 17 peter 123
3639 26 Apr 17 peter 124   // implementation of public API
3639 26 Apr 17 peter 125   template<typename T>
3639 26 Apr 17 peter 126   std::istream& getvector(std::istream& is, std::vector<T>& result,
3639 26 Apr 17 peter 127                           char delim, char newlinedelim)
3639 26 Apr 17 peter 128   {
4195 12 Aug 22 peter 129     return detail::getvector(is, result, [delim](char c) { return c==delim; },
4195 12 Aug 22 peter 130                              newlinedelim);
3639 26 Apr 17 peter 131   }
3639 26 Apr 17 peter 132
3639 26 Apr 17 peter 133
3639 26 Apr 17 peter 134   template<typename T>
3639 26 Apr 17 peter 135   std::istream& getvector(std::istream& is, std::vector<T>& result,
3639 26 Apr 17 peter 136                           const std::string& delim, char newlinedelim)
3639 26 Apr 17 peter 137   {
4195 12 Aug 22 peter 138     return detail::getvector(is, result, boost::is_any_of(delim), newlinedelim);
3639 26 Apr 17 peter 139   }
3639 26 Apr 17 peter 140
3639 26 Apr 17 peter 141 }}} // of namespace utility, yat, and theplu
3639 26 Apr 17 peter 142
3639 26 Apr 17 peter 143 #endif