2016-09-25 33 views
0

中的字符串表示形式差异抛出错误当字符串填充构造函数创建s(请参阅#5 http://www.cplusplus.com/reference/string/string/string/)时,我在调用strRom_map_intAra.at(s)时遇到超出范围的异常。内存字符串在map :: at()

当我声明并初始化一个字符串时,它返回期望的值。使用GDB我可以看到,从两种不同的方法值出现以不同的方式实现:s = "\001I" ... test = "I"c = 'I'

这是用字符串表示或与map::at()方法的问题?如果这两个变量都是字符串,为什么它们的实现细节很重要?

// Roman_int.cpp 
// Roman Constants 
extern const int M = 1000; 
extern const int CM = 900; 
extern const int D = 500; 
extern const int CD = 400; 
extern const int C = 100; 
extern const int XC = 90; 
extern const int L = 50; 
extern const int XL = 40; 
extern const int X = 10; 
extern const int IX = 9; 
extern const int V = 5; 
extern const int IV = 4; 
extern const int I = 1; 

extern const unordered_map<string, int> strRom_map_intAra 
{ 
    {"M",M}, 
    {"CM",CM}, 
    {"D",D}, 
    {"CD",CD}, 
    {"C",C}, 
    {"XC",XC}, 
    {"L",L}, 
    {"XL",XL}, 
    {"X",X}, 
    {"IX",IX}, 
    {"V",V}, 
    {"IV",IV}, 
    {"I",I} 
}; 

istream& operator>>(istream& is, Roman_int& r) 
{ 
    // throw exception if stream bad() 
    is.exceptions(is.exceptions()|ios_base::badbit); 

    string romStr; 
    get_contig_str(is,romStr); 
    vector<int> intRoms; 
    for (char c : romStr) 
    { 
      string s{1,c}; 
      string test = "I"; 
      intRoms.push_back(strRom_map_intAra.at(s)); 
    } 
//... 

// GDB Snippit 
142    for (char c : romStr) 
(gdb) 
144      string s{1,c}; 
(gdb) print c 
$1 = 73 'I' 
(gdb) n 
145      string test = "I"; 
(gdb) print s 
$2 = "\001I" 
(gdb) n 
146      intRoms.push_back(strRom_map_intAra.at(s)); 
(gdb) print test 
$3 = "I" 

因此,要回顾:GDB显示c = 'I' , s{1,c} = "\001I" , test = "I" strRom_map_intAra.at(s)结果out-of-range异常而test不使用

string s(1,c); 

代替

于F
string s{1,c}; 

看不

回答

3

尝试ollowing程序

#include <iostream> 

int main() 
{ 
    std::string s1(1, 'I'); 
    std::string s2{1, 'I'}; 

    std::cout << "size s1: " << s1.size() << std::endl; 
    std::cout << "size s2: " << s2.size() << std::endl; 
} 

它的输出是

size s1: 1 
size s2: 2 

这是因为与

std::string s1(1, 'I'); 

你调用一个构造器是你inizialize字符串以给定大小(1,在这种情况下)和所有使用给定字符初始化的字符(在本例中为I)。

随着

std::string s2{1, 'I'}; 

你inizialize你的字符串,字符的列表:

  • 的值为1的字符('\x01'

  • 和字符内'I'