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

字符串坐标提取场景下如何使用try-catch处理异常?

C++坐标字符串提取的异常处理方案

问题1:处理非预期分隔符的异常

当字符串中出现&这类替代预期的,或*的符号时,可在分割、格式校验逻辑中主动识别异常符号,抛出带提示的异常,再通过try-catch捕获输出对应信息。

实现逻辑

  1. 先清理字符串首尾的(、)、;及多余空格
  2. 遍历字符串检查是否存在非预期符号,同时验证每个坐标段是否符合数字 * SCALE的格式
  3. 发现异常符号时抛出包含错误提示的异常,在catch块中输出具体问题

代码示例

#include <iostream>
#include <string>
#include <stdexcept>
#include <algorithm>

// 预处理字符串,去除首尾无关字符
std::string preprocess(const std::string& str) {
    size_t start = str.find_first_not_of("( ");
    size_t end = str.find_last_not_of("); ");
    if (start == std::string::npos || end == std::string::npos) {
        throw std::invalid_argument("无效的坐标格式");
    }
    return str.substr(start, end - start + 1);
}

// 检查单个坐标段的格式是否合法
void check_segment_format(const std::string& segment) {
    size_t star_pos = segment.find('*');
    if (star_pos == std::string::npos) {
        size_t wrong_pos = segment.find_first_not_of("0123456789 SCALE");
        if (wrong_pos != std::string::npos) {
            char wrong_char = segment[wrong_pos];
            throw std::invalid_argument("该行应使用'*'而非'" + std::string(1, wrong_char) + "'");
        }
        throw std::invalid_argument("坐标段缺少'*'分隔符");
    }
}

// 分割坐标段并检查逗号分隔是否合法
std::vector<std::string> split_segments(const std::string& processed_str) {
    std::vector<std::string> segments;
    size_t pos = 0;
    size_t next_pos;
    while ((next_pos = processed_str.find(',', pos)) != std::string::npos) {
        std::string seg = processed_str.substr(pos, next_pos - pos);
        seg.erase(std::remove_if(seg.begin(), seg.end(), isspace), seg.end());
        segments.push_back(seg);
        pos = next_pos + 1;
    }
    std::string last_seg = processed_str.substr(pos);
    last_seg.erase(std::remove_if(last_seg.begin(), last_seg.end(), isspace), last_seg.end());
    segments.push_back(last_seg);

    // 检查是否存在非逗号的分隔符
    size_t wrong_sep_pos = processed_str.find_first_not_of("0123456789 * SCALE,");
    if (wrong_sep_pos != std::string::npos) {
        char wrong_char = processed_str[wrong_sep_pos];
        throw std::invalid_argument("该行应使用','而非'" + std::string(1, wrong_char) + "'");
    }
    return segments;
}

int main() {
    // 错误输入示例1
    std::string str1 = "(94 * SCALE & 10 * SCALE, 62 * SCALE, 10 * SCALE);";
    try {
        std::string processed = preprocess(str1);
        std::vector<std::string> segments = split_segments(processed);
        for (const auto& seg : segments) {
            check_segment_format(seg);
        }
    } catch (const std::invalid_argument& e) {
        std::cout << e.what() << std::endl; // 输出:该行应使用','而非'&'
    }

    // 错误输入示例2
    std::string str2 = "(94 & SCALE , 10 * SCALE, 62 * SCALE, 10 * SCALE);";
    try {
        std::string processed = preprocess(str2);
        std::vector<std::string> segments = split_segments(processed);
        for (const auto& seg : segments) {
            check_segment_format(seg);
        }
    } catch (const std::invalid_argument& e) {
        std::cout << e.what() << std::endl; // 输出:该行应使用'*'而非'&'
    }

    return 0;
}

问题2:处理字符串无法转换为整数的异常

stoi转换失败时会抛出std::invalid_argument(非数字格式)或std::out_of_range(数字超出整数范围)异常,直接捕获这些异常并输出对应提示即可。

实现逻辑

  1. 从坐标段中提取数字部分字符串
  2. 用try包裹stoi转换操作
  3. 捕获转换异常,抛出带具体信息的提示

代码示例

#include <iostream>
#include <string>
#include <stdexcept>
#include <algorithm>

std::string preprocess(const std::string& str) {
    size_t start = str.find_first_not_of("( ");
    size_t end = str.find_last_not_of("); ");
    if (start == std::string::npos || end == std::string::npos) {
        throw std::invalid_argument("无效的坐标格式");
    }
    return str.substr(start, end - start + 1);
}

std::vector<std::string> split_segments(const std::string& processed_str) {
    std::vector<std::string> segments;
    size_t pos = 0;
    size_t next_pos;
    while ((next_pos = processed_str.find(',', pos)) != std::string::npos) {
        std::string seg = processed_str.substr(pos, next_pos - pos);
        seg.erase(std::remove_if(seg.begin(), seg.end(), isspace), seg.end());
        segments.push_back(seg);
        pos = next_pos + 1;
    }
    std::string last_seg = processed_str.substr(pos);
    last_seg.erase(std::remove_if(last_seg.begin(), last_seg.end(), isspace), last_seg.end());
    segments.push_back(last_seg);
    return segments;
}

int extract_coordinate(const std::string& segment) {
    size_t star_pos = segment.find('*');
    if (star_pos == std::string::npos) {
        throw std::invalid_argument("坐标段缺少'*'分隔符");
    }
    std::string num_str = segment.substr(0, star_pos);
    num_str.erase(std::remove_if(num_str.begin(), num_str.end(), isspace), num_str.end());
    try {
        return std::stoi(num_str);
    } catch (const std::invalid_argument& e) {
        throw std::invalid_argument("无法将'" + num_str + "'转换为整数");
    } catch (const std::out_of_range& e) {
        throw std::invalid_argument("数字'" + num_str + "'超出整数范围");
    }
}

int main() {
    // 错误输入示例:数字部分为非整数
    std::string str = "(abc * SCALE, 10 * SCALE, 62 * SCALE, 10 * SCALE);";
    try {
        std::string processed = preprocess(str);
        std::vector<std::string> segments = split_segments(processed);
        for (const auto& seg : segments) {
            int coord = extract_coordinate(seg);
            std::cout << "提取的坐标值:" << coord << std::endl;
        }
    } catch (const std::invalid_argument& e) {
        std::cout << e.what() << std::endl; // 输出:无法将'abc'转换为整数
    }

    return 0;
}

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.08.25 01:18:14