Search code examples
c++stringc++11tostring

Making a user-defined class std::to_string-able


I know it seems too much Java or C#. However, is it possible/good/wise to make my own class valid as an input for the function std::to_string ? Example:

class my_class{
public:
std::string give_me_a_string_of_you() const{
    return "I am " + std::to_string(i);
}
int i;
};

void main(){
    my_class my_object;
    std::cout<< std::to_string(my_object);
}

If there is no such thing (and I think that), what is the best way to do it?


Solution

  • First, some ADL helping:

    namespace notstd {
      namespace adl_helper {
        template<class T>
        std::string as_string( T&& t ) {
          using std::to_string;
          return to_string( std::forward<T>(t) );
        }
      }
      template<class T>
      std::string to_string( T&& t ) {
        return adl_helper::as_string(std::forward<T>(t));
      }
    }
    

    notstd::to_string(blah) will do an ADL-lookup of to_string(blah) with std::to_string in scope.

    We then modify your class:

    class my_class{
    public:
      friend std::string to_string(my_class const& self) {
        return "I am " + notstd::to_string(self.i);
      }
      int i;
    };
    

    and now notstd::to_string(my_object) finds the proper to_string, as does notstd::to_string(7).

    With a touch more work, we can even support .tostring() methods on types to be auto-detected and used.

    Live example