问题
Abstract: I was expecting the code: cout << uint8_t(0); to print "0", but it doesn't print anything.
Long version: When I try to stream uint8_t objects to cout, I get strange characters with gcc. Is this expected behavior? Could it be that uint8_t is an alias for some char-based type? See compiler/system notes in the code example.
// compile and run with:
// g++ test-uint8.cpp -std=c++11 && ./a.out
// -std=c++0x (for older gcc versions)
/**
* prints out the following with compiler:
* gcc (GCC) 4.7.2 20120921 (Red Hat 4.7.2-2)
* on the system:
* Linux 3.7.9-101.fc17.x86_64
* Note that the first print statement uses an unset uint8_t
* and therefore the behaviour is undefined. (Included here for
* completeness)
> g++ test-uint8.cpp -std=c++11 && ./a.out
>>>�<<< >>>194<<<
>>><<< >>>0<<<
>>><<< >>>0<<<
>>><<< >>>0<<<
>>><<< >>>1<<<
>>><<< >>>2<<<
*
**/
#include <cstdint>
#include <iostream>
void print(const uint8_t& n)
{
std::cout << ">>>" << n << "<<< "
<< ">>>" << (unsigned int)(n) << "<<<\n";
}
int main()
{
uint8_t a;
uint8_t b(0);
uint8_t c = 0;
uint8_t d{0};
uint8_t e = 1;
uint8_t f = 2;
for (auto i : {a,b,c,d,e,f})
{
print(i);
}
}
回答1:
uint8_t is an alias for unsigned char, and the iostreams have special overloads for chars that print out the characters rather than formatting numbers.
The conversion to integer inhibits this.
回答2:
Could it be that uint8_t is an alias for some char-based type?
Absolutely. It's required to be a typedef for a builtin 8-bit unsigned integral type, if such a type exists. Since there are only two possible 8-bit unsigned integral types, char for a compiler that treats it as unsigned and unsigned char, it must be one of those. Except on systems where char is larger than 8 bits, in which case it won't exist.
回答3:
As others have pointed out, uint8_t is streamed as an unsigned char. I've sometimes made use of bit fields from integer types that are streamed as, well, integers, to avoid having to cast or overload operator<<, but only when it doesn't waste space, like in the Pos struct below:
#include <iostream>
struct WasteAbyte {
unsigned short has_byte_range:8;
};
struct Pos {
unsigned short x:8;
unsigned short y:8;
};
int main() {
WasteAbyte W = {255};
++W.has_byte_range;
std::cout << W.has_byte_range << std::endl;
std::cout << sizeof(WasteAbyte) << std::endl;
std::cout << sizeof(Pos) << std::endl;
return 0;
}
Output:
0
2
2
来源:https://stackoverflow.com/questions/15296661/uint8-t-iostream-behavior