在C++中,要打印十六进制数字,请执行以下操作:

int num = 10;
std::cout << std::hex << num; // => 'a'

我知道我可以创建一个仅向流中添加内容的操纵器,如下所示:
std::ostream& windows_feed(std::ostream& out)
{
    out << "\r\n";
    return out;
}

std::cout << "Hello" << windows_feed; // => "Hello\r\n"

但是,如何创建一个类似于“hex”的操纵器来修改要出现在流中的项目?作为一个简单的示例,我将如何在这里创建plusone机械手?:
int num2 = 1;
std::cout << "1 + 1 = " << plusone << num2; // => "1 + 1 = 2"

// note that the value stored in num2 does not change, just its display above.
std::cout << num2; // => "1"

最佳答案

首先,您必须将一些状态存储到每个流中。您可以使用 iword 函数和传递给它的索引(由 xalloc 给出)来实现:

inline int geti() {
    static int i = ios_base::xalloc();
    return i;
}

ostream& add_one(ostream& os) { os.iword(geti()) = 1; return os; }
ostream& add_none(ostream& os) { os.iword(geti()) = 0; return os; }

将其放置在适当的位置,您已经可以在所有流中检索某些状态。现在,您只需要加入相应的输出操作即可。数值输出由构面完成,因为它可能取决于语言环境。所以你可以做
struct my_num_put : num_put<char> {
    iter_type
    do_put(iter_type s, ios_base& f, char_type fill, long v) const {
        return num_put<char>::do_put(s, f, fill, v + f.iword(geti()));
    }

    iter_type
    do_put(iter_type s, ios_base& f, char_type fill, unsigned long v) const {
        return num_put<char>::do_put(s, f, fill, v + f.iword(geti()));
    }
};

现在,您可以测试这些东西了。
int main() {
    // outputs: 11121011
    cout.imbue(locale(locale(),new my_num_put));
    cout << add_one << 10 << 11
         << add_none << 10 << 11;
}

如果您只想增加下一个数字,只需在每次调用0之后再次将单词设置为do_put即可。

09-18 17:20