代码之家  ›  专栏  ›  技术社区  ›  PeterK

如何保存C++流的格式化?

  •  1
  • PeterK  · 技术社区  · 14 年前

    我有以下代码(简化):

    ostringstream oss;
    
    oss << "Text ";
    
    oss << hex << uppercase;
    oss.width(8);
    oss.fill('0');
    
    oss << var1 << " ";
    oss << var2 << " ";
    
    oss << dec << nouppercase;
    oss.width(1);
    
    oss << var3 << " another text." << endl;
    
    string result = oss.str();
    // work with result...
    

    在哪里? var1 , var2 unsigned int S和 var3 是一个 int . 我们的想法是创建一个字符串 VAR1 VAR2 被格式化为十六进制数(但没有 0x ) VAR3 作为常规整数。我发现只有第一个数字格式正确,第二个数字没有用零填充:

    Text 000AF00C 3B7FF 1 another text.
    

    过了一会儿,我发现设置宽度和填充参数会再次修复这个问题。有没有一种方法可以避免为每个数字反复指定这些格式化规则?格式化变量的数量远远高于2,这只是一个简化的例子。将所有这些包装到函数中是一个选项,但是我真的想学习如何使用 ostringstream .

    4 回复  |  直到 14 年前
        1
  •  4
  •   codymanix    14 年前

    抱歉,流格式的一些设置称为volatile(与关键字无关),您必须每次都设置它。 See here for explanation.

    最好创建自己的函数。

        2
  •  3
  •   Community skywinder    7 年前

    有没有一种方法可以避免为每个数字反复指定这些格式化规则?

    不, there are manipulators which are sticky and there are those which are not . 那些不必为每个输出重复的。

    顺便说一句,你可以用一些句法上的甜头

    oss.width(8);
    oss.fill('0');
    
    oss << var1 << " ";
    

    进入之内

    oss << std::setw(8) << std::setfill('0') << var1 << " ";
    
        3
  •  1
  •   anon    14 年前

    一如既往,编写一个函数:

    void WriteHex( unsigned int n, ostream & os  ) {
      os << hex << uppercase;
      os.width(8);
      os.fill('0');
      os << n;
    }
    
        4
  •  0
  •   CB Bailey    14 年前

    除了 width 仅在下一个格式化输出操作之前保留。这是因为格式化输出函数需要调用 width(0) 作为副作用。

    一个相当简洁的解决方案是使用 setw 需要非零宽度的输出操作之前的操纵器。

    注意,如果您已经设置了填充字符,并且从最后一个数字输出中保留了8的宽度,那么您可能会对此输出感到惊讶。

    os << " ";