当前位置:  开发笔记 > 编程语言 > 正文

在C++中检查变量类型

如何解决《在C++中检查变量类型》经验,为你挑选了2个好方法。

所以我目前正在学习C++,并决定制作一个测试我迄今为止学到的技能的程序.现在在我的代码中我想检查用户输入的值是否为double,如果它不是double,我将放置if循环并要求它们重新输入.我遇到的问题是如何检查用户输入的变量类型,如果用户输入字符或字符串,我可以输出错误消息.这是我的代码:

//cubes a user entered number
#include 
using namespace std;

double cube(double n); //function prototype

int main()
{
    cout << "Enter the number you want to cube: "; //ask user to input number
    double user;
    cin >> user;  //user entering the number

    cout << "The cube of " << user << " is " << cube(user) << "." << endl; //displaying the cubed number

    return 0;
}

double cube (double n) //function that cubes the number
{
    return n*n*n; // cubing the number and returning it
}

编辑:我不得不说我刚开始并且对你的代码没有丝毫的线索,但我会查看你的链接.顺便说一句,我还没有学习如何使用模板,我正在学习如何处理数据,只有我的C++ Primer Plus第5版第3章.



1> Johannes Sch..:

安全的C++方式

您可以使用以下方法为此定义函数std::istringstream:

#include   

bool is_double(std::string const& str) {
    std::istringstream ss(str);

    // always keep the scope of variables as close as possible. we see
    // 'd' only within the following block.
    {
        double d;
        ss >> d;
    }

    /* eat up trailing whitespace if there was a double read, and ensure
     * there is no character left. the eof bit is set in the case that
     * `std::ws` tried to read beyond the stream. */
    return (ss && (ss >> std::ws).eof());
}

为了帮助您弄清楚它的作用(简化了一些要点):

创建一个用给定字符串初始化的输入字符串流

用它读取双值operator>>.这意味着跳过空格并尝试读取双精度数.

如果没有可以读取双精度,则在abc流中设置失败位.请注意,类似的情况3abc将成功,并且不会设置失败位.

如果设置了失败位,则ss计算为零值,这意味着为false.

如果读取了double,我们会跳过尾随空格.然后如果我们是在流结束(注意,eof()将返回,如果我们试图读取过去的结束.std::ws正是这么做的),eof将返回true.请注意,此检查确保3abc不会通过我们的检查.

如果两个case,right和left of &&evaluate为true,我们返回true给调用者,表示给定的字符串是double.

类似,你检查int和其他类型.如果您知道如何使用模板,那么您也知道如何将其概括为其他类型.顺便说一下,这正是boost::lexical_cast为您提供的.请查看:http://www.boost.org/doc/libs/1_37_0/libs/conversion/lexical_cast.htm.

C Way One

这种方式有优点(快速)但也有主要缺点(不能使用模板推广,需要使用原始指针):

#include 
#include   

bool is_double(std::string const& s) {
    char * endptr;
    std::strtod(s.c_str(), &endptr);
    if(endptr != s.c_str()) // skip trailing whitespace
        while(std::isspace(*endptr)) endptr++;
    return (endptr != s.c_str() && *endptr == '\0');
}

strtod将设置endptr为处理的最后一个字符.在我们的例子中,终止空字符.如果未执行转换,则将endptr设置为给定的字符串的值strtod.

C方式二

一个可能成功的事情std::sscanf.但是监督某些事情很容易.这是正确的方法:

#include 

bool is_double(std::string const& s) {
    int n;
    double d;
    return (std::sscanf(s.c_str(), "%lf %n", &d, &n) >= 1 && 
            n == static_cast(s.size()));
}

std::sscanf将返回转换的项目.虽然标准规定%n不包括在该计数中,但是几个来源相互矛盾.最好进行比较>=以使其正确(参见手册页sscanf).n将被设置为已处理字符的数量.它与字符串的大小进行比较.两个格式说明符之间的空格占可选的尾部空格.

结论

如果您是初学者,请std::stringstream以C++方式阅读并执行此操作.在你对C++的一般概念感觉良好之前,最好不要乱用指针.



2> Federico A. ..:

没有合适的方法来检查字符串是否真的包含标准库中的double.您可能想要使用Boost.以下解决方案的灵感来自C++ Cookbook中的配方3.3 :

#include 
#include 
using namespace std;
using namespace boost;

double cube(double n);

int main()
{
    while(true)
    {
        cout << "Enter the number you want to cube: ";
        string user;
        cin >> user;

        try
        {
            // The following instruction tries to parse a double from the 'user' string.
            // If the parsing fails, it raises an exception of type bad_lexical_cast.
            // If an exception is raised within a try{ } block, the execution proceeds
            // with one of the following catch() blocks
            double d = lexical_cast  (user);   

            cout << "The cube of " << d << " is " << cube(d) << "." << endl;
            break;
        }
        catch(bad_lexical_cast &e)
        {
            // This code is executed if the lexical_cast raised an exception; We
            // put an error message and continue with the loop
            cout << "The inserted string was not a valid double!" << endl;
        }
    }
    return 0;
}

double cube (double n)
{
    return n*n*n;
}

推荐阅读
重庆制造漫画社
这个屌丝很懒,什么也没留下!
DevBox开发工具箱 | 专业的在线开发工具网站    京公网安备 11010802040832号  |  京ICP备19059560号-6
Copyright © 1998 - 2020 DevBox.CN. All Rights Reserved devBox.cn 开发工具箱 版权所有