繁体   English   中英

十六进制<< setw()<< setfill()不适用于指针值输出

[英]hex << setw() << setfill() doesn't work with pointer value output

Win7-64
cygwin的
Netbeans 7.4
gcc(cygwin)4.8.3

编译器调用

g++ -Wall -Wno-reorder -Wno-unused-value -c -g -MMD -MP -MF

任何原因输出和预期输出不同? 我没想到“ 0x”前缀。

Output   << SlipHashEntry::create      0x22a000 list3
Expected << SlipHashEntry::create      0x000000000022a000 list3

Output   << SlipDescription::delete    0x600062d50 list5
Expected << SlipDescription::delete    0x0000000600062d50 list5

这是相关的代码片段

SlipHashEntry::SlipHashEntry
    ( const string& name, void* ptr, Type type, int debugFlag )
: completeFlag(false)
, debugFlag(debugFlag)
, hashDebugFlag((bool)(debugFlag & SlipRead::HASH))
, inputDebugFlag((bool)(debugFlag & SlipRead::INPUT))
, leakDebugFlag((bool)(debugFlag & SlipRead::LEAK))
, descriptorChain(NULL)
, link(NULL)
, name(new string(name))
, nestedPtr(NULL)
, ptr(ptr)
, type(type) { 
    DEBUG(leakDebugFlag,
    cout << left << setw(27) << setfill(' ') << "SlipHashEntry::create " 
         << hex << setw(sizeof(void*)) 
         << setfill('0') << (void*)this << ' ' << name <<endl;)
}; 

“输出与预期输出不同的任何原因?我没想到前缀“ 0x”。”

关于输出中的0x前缀,这是由std::ostream& operator<<(std::ostream&, const void*)的内部运算符重载完成的, std::ostream& operator<<(std::ostream&, const void*) 参见(7)

另外,您对setw()有一些误解:您应该记住, setw()设置以字符(即数字)表示的字段大小。 您要显示一个64位指针,该指针等效于8个字节,每个位数代表2位

      cout << left << setw(27) << setfill(' ') << "SlipHashEntry::create " 
           << hex << setw(2 * sizeof(void*)) 
                       // ^^^
           << setfill('0') << (void*)this << ' ' << name <<endl;)

只需将指针大小(以字节为单位)乘以2,即可获得完整位数的正确字段宽度。

尽管void*的内在输出运算符定义不能完全满足您的要求。
当我尝试根据上面的说明制作在线可编译示例时,我注意到您实际上无法操纵内部指针输出格式。 我组成了一个简单的示例,如何实现所需的固定8字节格式:

#include <iostream>
#include <iomanip>

// A simple manipulator to format pointers in a fixed length format (according 
// 64 bit) with leading zeroes and a "0x" prefix
class fmt_longptr {
public:
    fmt_longptr(void* ptr) : ptr_(ptr) {}
    void put(std::ostream& os) const {
        os << "0x" << std::hex << std::setw(2 * sizeof(void*)) 
           << std::setfill('0') << (unsigned long)ptr_;
    }
private:
    friend std::ostream& operator<<(std::ostream& os, const fmt_longptr& fmt);
    void* ptr_;
};

std::ostream& operator<<(std::ostream& os, const fmt_longptr& fmt) {
    fmt.put(os);
    return os;
}

这是使用方法,并显示了与固有指针格式的区别

int main() {
    int a;

    std::cout << std::setfill('0') << std::setw(2 * sizeof(void*)) << &a 
              << std::endl;
    std::cout << fmt_longptr(&a) << std::endl;
    return 0;
}

产量

000x7fff270d987c
0x00007fff270d987c

这是在线工作示例

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM