简体   繁体   中英

On the conversion from std::string type to template T type in C++

I've found on this forum the following snippet witten by user Ben Voigt:

//forward declaration
template<typename T>
T getline_as(std::istream& s);

template<>
std::string getline_as<std::string>(std::istream& s)
{
    std::string str;
    std::getline(s,str);
    return str;
} 

template<typename T>
T getline_as(std::istream& s)
{
    std::stringstream convert(getline_as<std::string>(s));

    T value;
    convert >> value;
    return value;
}

I am looking for a way to handle possible failures of convert >> value; . My goal would be to iterate the request to the user to make it insert a given input correctly:

int main()
{
    std::cout << "Please enter a number: ";
    double number{getline_as<double>(std::cin)};
}

My idea was to create a do-while loop inside getline_as but I can't make it work.

template<typename T>
T getline_as(std::istream& s)
{
    std::stringstream convert;
    T value;
    do
    {
        convert(getline_as<std::string>(s));
    }
    while(!(convert >> value));
    return value;
}

std::stringstream convert(...); is a constructor call, but trying to do convert(...); after the stream is created is illegal (it would require the stream to overload operator() , which it doesn't do). convert = std::stringstream(...) would work, but I'd just completely recreate the stream.

You also should use a read-only std::istringstream , since you never write anything to it.

I also made some cosmetic changes and ended up with following:

template <typename T>
[[nodiscard]] T getline_as(std::istream &s);

template <>
[[nodiscard]] std::string getline_as<std::string>(std::istream &s)
{
    std::string str;
    std::getline(s, str);
    return str;
} 

template <typename T>
[[nodiscard]] T getline_as(std::istream &s)
{
    while (true)
    {
        T value{};
        std::istringstream convert(getline_as<std::string>(s));
        if (convert >> value)
            return value;
    }
}

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM