18cfa702f803c5ef6a2b062a489a1b2cf66b45b5eMike Dodd/** 28cfa702f803c5ef6a2b062a489a1b2cf66b45b5eMike Dodd * @file string_manip.h 38cfa702f803c5ef6a2b062a489a1b2cf66b45b5eMike Dodd * std::string helpers 48cfa702f803c5ef6a2b062a489a1b2cf66b45b5eMike Dodd * 58cfa702f803c5ef6a2b062a489a1b2cf66b45b5eMike Dodd * @remark Copyright 2002 OProfile authors 68cfa702f803c5ef6a2b062a489a1b2cf66b45b5eMike Dodd * @remark Read the file COPYING 78cfa702f803c5ef6a2b062a489a1b2cf66b45b5eMike Dodd * 88cfa702f803c5ef6a2b062a489a1b2cf66b45b5eMike Dodd * @author Philippe Elie 98cfa702f803c5ef6a2b062a489a1b2cf66b45b5eMike Dodd * @author John Levon 108cfa702f803c5ef6a2b062a489a1b2cf66b45b5eMike Dodd */ 118cfa702f803c5ef6a2b062a489a1b2cf66b45b5eMike Dodd 128cfa702f803c5ef6a2b062a489a1b2cf66b45b5eMike Dodd#ifndef STRING_MANIP_H 138cfa702f803c5ef6a2b062a489a1b2cf66b45b5eMike Dodd#define STRING_MANIP_H 148cfa702f803c5ef6a2b062a489a1b2cf66b45b5eMike Dodd 158cfa702f803c5ef6a2b062a489a1b2cf66b45b5eMike Dodd#include <string> 168cfa702f803c5ef6a2b062a489a1b2cf66b45b5eMike Dodd#include <vector> 178cfa702f803c5ef6a2b062a489a1b2cf66b45b5eMike Dodd#include <sstream> 188cfa702f803c5ef6a2b062a489a1b2cf66b45b5eMike Dodd#include <stdexcept> 198cfa702f803c5ef6a2b062a489a1b2cf66b45b5eMike Dodd 208cfa702f803c5ef6a2b062a489a1b2cf66b45b5eMike Dodd/** 218cfa702f803c5ef6a2b062a489a1b2cf66b45b5eMike Dodd * @param str string 228cfa702f803c5ef6a2b062a489a1b2cf66b45b5eMike Dodd * @param ch the characterto search 238cfa702f803c5ef6a2b062a489a1b2cf66b45b5eMike Dodd * 248cfa702f803c5ef6a2b062a489a1b2cf66b45b5eMike Dodd * erase char from the begin of str to the last 258cfa702f803c5ef6a2b062a489a1b2cf66b45b5eMike Dodd * occurence of ch from and return the string 268cfa702f803c5ef6a2b062a489a1b2cf66b45b5eMike Dodd */ 278cfa702f803c5ef6a2b062a489a1b2cf66b45b5eMike Doddstd::string erase_to_last_of(std::string const & str, char ch); 288cfa702f803c5ef6a2b062a489a1b2cf66b45b5eMike Dodd 298cfa702f803c5ef6a2b062a489a1b2cf66b45b5eMike Dodd/// split string s by first occurence of char c, returning the second part. 308cfa702f803c5ef6a2b062a489a1b2cf66b45b5eMike Dodd/// s is set to the first part. Neither include the split character 318cfa702f803c5ef6a2b062a489a1b2cf66b45b5eMike Doddstd::string split(std::string & s, char c); 328cfa702f803c5ef6a2b062a489a1b2cf66b45b5eMike Dodd 338cfa702f803c5ef6a2b062a489a1b2cf66b45b5eMike Dodd/// return true if "prefix" is a prefix of "s", behavior is undefined 348cfa702f803c5ef6a2b062a489a1b2cf66b45b5eMike Dodd/// if prefix is an empty string 358cfa702f803c5ef6a2b062a489a1b2cf66b45b5eMike Doddbool is_prefix(std::string const & s, std::string const & prefix); 368cfa702f803c5ef6a2b062a489a1b2cf66b45b5eMike Dodd 378cfa702f803c5ef6a2b062a489a1b2cf66b45b5eMike Dodd/** 388cfa702f803c5ef6a2b062a489a1b2cf66b45b5eMike Dodd * @param str the string to tokenize 398cfa702f803c5ef6a2b062a489a1b2cf66b45b5eMike Dodd * @param sep the separator_char 408cfa702f803c5ef6a2b062a489a1b2cf66b45b5eMike Dodd * 418cfa702f803c5ef6a2b062a489a1b2cf66b45b5eMike Dodd * separate fields in a string in a list of token; field are 428cfa702f803c5ef6a2b062a489a1b2cf66b45b5eMike Dodd * separated by the sep character, sep char can be escaped 438cfa702f803c5ef6a2b062a489a1b2cf66b45b5eMike Dodd * by '\\' to specify a sep char in a token, '\\' not followed 448cfa702f803c5ef6a2b062a489a1b2cf66b45b5eMike Dodd * by a sep is taken as it e.g. "\,\a" --> ",\a" 458cfa702f803c5ef6a2b062a489a1b2cf66b45b5eMike Dodd */ 468cfa702f803c5ef6a2b062a489a1b2cf66b45b5eMike Doddstd::vector<std::string> separate_token(std::string const & str, char sep); 478cfa702f803c5ef6a2b062a489a1b2cf66b45b5eMike Dodd 488cfa702f803c5ef6a2b062a489a1b2cf66b45b5eMike Dodd/// remove trim chars from start of input string return the new string 498cfa702f803c5ef6a2b062a489a1b2cf66b45b5eMike Doddstd::string ltrim(std::string const & str, std::string const & totrim = "\t "); 508cfa702f803c5ef6a2b062a489a1b2cf66b45b5eMike Dodd/// remove trim chars from end of input string return the new string 518cfa702f803c5ef6a2b062a489a1b2cf66b45b5eMike Doddstd::string rtrim(std::string const & str, std::string const & totrim = "\t "); 528cfa702f803c5ef6a2b062a489a1b2cf66b45b5eMike Dodd/// ltrim(rtrim(str)) 538cfa702f803c5ef6a2b062a489a1b2cf66b45b5eMike Doddstd::string trim(std::string const & str, std::string const & totrim = "\t "); 548cfa702f803c5ef6a2b062a489a1b2cf66b45b5eMike Dodd 558cfa702f803c5ef6a2b062a489a1b2cf66b45b5eMike Dodd/** 568cfa702f803c5ef6a2b062a489a1b2cf66b45b5eMike Dodd * format_percent - smart format of double percentage value 578cfa702f803c5ef6a2b062a489a1b2cf66b45b5eMike Dodd * @param value - the value 588cfa702f803c5ef6a2b062a489a1b2cf66b45b5eMike Dodd * @param int_width - the maximum integer integer width default to 2 598cfa702f803c5ef6a2b062a489a1b2cf66b45b5eMike Dodd * @param frac_width - the fractionnary width default to 4 608cfa702f803c5ef6a2b062a489a1b2cf66b45b5eMike Dodd * @param showpos - show + sign for positive values 618cfa702f803c5ef6a2b062a489a1b2cf66b45b5eMike Dodd * 628cfa702f803c5ef6a2b062a489a1b2cf66b45b5eMike Dodd * This formats a percentage into exactly the given width and returns 638cfa702f803c5ef6a2b062a489a1b2cf66b45b5eMike Dodd * it. If the integer part is larger than the given int_width, the 648cfa702f803c5ef6a2b062a489a1b2cf66b45b5eMike Dodd * returned string will be wider. The returned string is never 658cfa702f803c5ef6a2b062a489a1b2cf66b45b5eMike Dodd * shorter than (fract_with + int_width + 1) 668cfa702f803c5ef6a2b062a489a1b2cf66b45b5eMike Dodd * 678cfa702f803c5ef6a2b062a489a1b2cf66b45b5eMike Dodd */ 688cfa702f803c5ef6a2b062a489a1b2cf66b45b5eMike Doddstd::string const 698cfa702f803c5ef6a2b062a489a1b2cf66b45b5eMike Doddformat_percent(double value, size_t int_width, 708cfa702f803c5ef6a2b062a489a1b2cf66b45b5eMike Dodd size_t frac_width, bool showpos = false); 718cfa702f803c5ef6a2b062a489a1b2cf66b45b5eMike Dodd 728cfa702f803c5ef6a2b062a489a1b2cf66b45b5eMike Dodd/// prefered width to format percentage 738cfa702f803c5ef6a2b062a489a1b2cf66b45b5eMike Doddstatic unsigned int const percent_int_width = 2; 748cfa702f803c5ef6a2b062a489a1b2cf66b45b5eMike Doddstatic unsigned int const percent_fract_width = 4; 758cfa702f803c5ef6a2b062a489a1b2cf66b45b5eMike Doddstatic unsigned int const percent_width = percent_int_width + percent_fract_width + 1; 768cfa702f803c5ef6a2b062a489a1b2cf66b45b5eMike Dodd 778cfa702f803c5ef6a2b062a489a1b2cf66b45b5eMike Dodd 788cfa702f803c5ef6a2b062a489a1b2cf66b45b5eMike Dodd/** 798cfa702f803c5ef6a2b062a489a1b2cf66b45b5eMike Dodd * @param src input parameter 808cfa702f803c5ef6a2b062a489a1b2cf66b45b5eMike Dodd * convert From src to a T through an istringstream. 818cfa702f803c5ef6a2b062a489a1b2cf66b45b5eMike Dodd * 828cfa702f803c5ef6a2b062a489a1b2cf66b45b5eMike Dodd * Throws invalid_argument if conversion fail. 838cfa702f803c5ef6a2b062a489a1b2cf66b45b5eMike Dodd * 848cfa702f803c5ef6a2b062a489a1b2cf66b45b5eMike Dodd * Note that this is not as foolproof as boost's lexical_cast 858cfa702f803c5ef6a2b062a489a1b2cf66b45b5eMike Dodd */ 868cfa702f803c5ef6a2b062a489a1b2cf66b45b5eMike Doddtemplate <typename To, typename From> 878cfa702f803c5ef6a2b062a489a1b2cf66b45b5eMike DoddTo op_lexical_cast(From const & src) 888cfa702f803c5ef6a2b062a489a1b2cf66b45b5eMike Dodd{ 898cfa702f803c5ef6a2b062a489a1b2cf66b45b5eMike Dodd std::ostringstream in; 908cfa702f803c5ef6a2b062a489a1b2cf66b45b5eMike Dodd if (!(in << src)) 918cfa702f803c5ef6a2b062a489a1b2cf66b45b5eMike Dodd throw std::invalid_argument("op_lexical_cast<T>()"); 928cfa702f803c5ef6a2b062a489a1b2cf66b45b5eMike Dodd std::istringstream out(in.str()); 938cfa702f803c5ef6a2b062a489a1b2cf66b45b5eMike Dodd To value; 948cfa702f803c5ef6a2b062a489a1b2cf66b45b5eMike Dodd if (!(out >> value)) { 958cfa702f803c5ef6a2b062a489a1b2cf66b45b5eMike Dodd throw std::invalid_argument("op_lexical_cast<T>(\"" + 968cfa702f803c5ef6a2b062a489a1b2cf66b45b5eMike Dodd in.str() +"\")"); 978cfa702f803c5ef6a2b062a489a1b2cf66b45b5eMike Dodd } 988cfa702f803c5ef6a2b062a489a1b2cf66b45b5eMike Dodd return value; 998cfa702f803c5ef6a2b062a489a1b2cf66b45b5eMike Dodd} 1008cfa702f803c5ef6a2b062a489a1b2cf66b45b5eMike Dodd 1018cfa702f803c5ef6a2b062a489a1b2cf66b45b5eMike Dodd// specialization accepting hexadecimal and octal number in input. Note that 1028cfa702f803c5ef6a2b062a489a1b2cf66b45b5eMike Dodd// op_lexical_cast<unsigned int>("0x23"); will fail because it call the 1038cfa702f803c5ef6a2b062a489a1b2cf66b45b5eMike Dodd// non specialized template. 1048cfa702f803c5ef6a2b062a489a1b2cf66b45b5eMike Doddtemplate <> 1058cfa702f803c5ef6a2b062a489a1b2cf66b45b5eMike Doddunsigned int op_lexical_cast<unsigned int>(std::string const & str); 1068cfa702f803c5ef6a2b062a489a1b2cf66b45b5eMike Dodd 1078cfa702f803c5ef6a2b062a489a1b2cf66b45b5eMike Dodd#endif /* !STRING_MANIP_H */ 108