You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

C++整数输入验证:构建仅匹配单组数字的正则表达式

整数输入验证器的正则匹配优化问题

我在学习C++课程时自制了一个整数输入验证器(非作业,属个人探索),用于处理各类数据源的未清洗松散输入并转换为整数。现有实现代码如下:

#include <cmath>
#include <iostream>
#include <regex>
#include <string>

using namespace std;

...
...

int validate_integer(const string& input) {
        return round(stof(regex_replace(input, regex(R"([^\-0-9.]+)"), "")));
}

该函数可将<2112>、{2112}、2112.0等输入解析为整数2112返回。

我希望添加正则匹配逻辑,当输入过于混乱(如含多组数字)时抛出std::invalid_argument异常,但构建合适正则表达式遇阻,已测试多个正则:

([0-9]+^0-9\.-\d+)
(.*[\.\-0-9.]*[^\d]+[^\d].*)
(.+|[\-\.0-9]+[^0-9]+(?![0-9]+))
((.+^[\-\.]*[0-9]+)|(^[\-\.]*[0-9]))+[^0-9]+[^0-9]+
(([^0-9]+[\-\.]*[0-9]+)|(^[\-\.]*[0-9]+)(?![^0-9]+[0-9]+))
.*[\d]+(?<![^0-9]+).*

有效输入

<2112>
[(2112)]
"2112,"
2112.0
-2112
<span style = "numeral">2112</span>

偏好有效输入

.2112  (应返回0)
21.12  (应返回21)
98.89  (应返回99)

无效输入

21,12
"21","12,"
<span style = "font-size:18.0pt">2112</span>
21TwentyOne12

你的核心思路是对的:先过滤非数字相关字符再转换,但当前实现的问题在于,过滤后可能会把多组数字合并成一个错误的数值(比如21,12过滤后变成2112,但这属于无效输入),所以需要先做有效性校验,再执行过滤转换。

解决方案

先通过正则判断输入是否仅包含一组可解析为数字的内容(即所有数字、-、.不能被非允许字符分割成多组),再进行后续处理:

  1. 校验用正则表达式
^[^0-9\-]*([\-]?(\d+\.?\d*|\.\d+))[^0-9]*$
  • ^[^0-9\-]*:开头允许任意非数字、非负号的字符
  • ([\-]?(\d+\.?\d*|\.\d+)):匹配合法数字(可选负号,支持整数、小数、纯小数格式,至少包含一个数字)
  • [^0-9]*$:结尾允许任意非数字的字符
  1. 修改后的函数实现
#include <cmath>
#include <iostream>
#include <regex>
#include <string>

using namespace std;

int validate_integer(const string& input) {
    // 前置校验:仅允许一组合法数字
    regex valid_pattern(R"(^[^0-9\-]*([\-]?(\d+\.?\d*|\.\d+))[^0-9]*$)");
    if (!regex_match(input, valid_pattern)) {
        throw invalid_argument("Input contains multiple number groups or invalid format");
    }

    // 过滤无关字符
    string cleaned = regex_replace(input, regex(R"([^\-0-9.]+)"), "");
    
    // 处理纯小数点特殊情况(如".2112"转换后round为0)
    if (cleaned == "." || cleaned == "-.") {
        return 0;
    }

    return round(stof(cleaned));
}
  1. 测试验证
  • 有效输入:全部匹配正则,过滤转换后结果符合预期
  • 偏好有效输入:.2112匹配正则,转换后round为0;21.12round为21;98.89round为99,满足需求
  • 无效输入:均不匹配正则,会抛出invalid_argument异常,符合要求

整体思路方向没问题,补上前置的正则校验步骤,就能准确识别多组数字的无效输入,避免错误转换。

内容的提问来源于stack exchange,提问作者Stephan Peters

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.06.28 14:10:20