Using cout to print hex values; surely you can't be serious

  • Thread starter Chris Stankevitz
  • Start date
C

Chris Stankevitz

char c = 0xFF;

Q1: How do I use cout to print the variable c so that it appears at
stdout as "FF"?

A1:
#include <iomanip>
#include <iostream>

std::cout << std::hex << std::setfill('0') << std::setw(2) <<
std::uppercase << (static_cast<int>(c) & 0xFF);

Q2: Surely you can't be serious.

A2: I am serious. And don't call me Shirley.
 
V

Victor Bazarov

char c = 0xFF;

Have you considered that 0xFF is outside the range a signed 'char' is
guaranteed to represent? Or is your 'char' unsigned by default? Just
checking...
Q1: How do I use cout to print the variable c so that it appears at
stdout as "FF"?

A1:
#include<iomanip>
#include<iostream>

std::cout<< std::hex<< std::setfill('0')<< std::setw(2)<<
std::uppercase<< (static_cast<int>(c)& 0xFF);

Q2: Surely you can't be serious.

A2: I am serious. And don't call me Shirley.

Similar to "How do I put my trousers on by pulling them over my head?".

Use 'printf', it seems to suit *this particular task* better.

V
 
S

Stefan Ram

Chris Stankevitz said:
Q1: How do I use cout to print the variable c so that it appears at
stdout as "FF"?
std::cout << std::hex << std::setfill('0') << std::setw(2) <<
std::uppercase << (static_cast<int>(c) & 0xFF);

This is not guaranteed to print »FF« as required.

Maybe you wanted to print a hexadecimal representation of
the value of c as »FF«?

{ assert c == 0xff; ::std::cout << "FF"; }
 
G

gwowen

On 2/8/2012 12:16 AM, Chris Stankevitz wrote:

Use 'printf', it seems to suit *this particular task* better.

But sometimes you want to mix streaming objects with a custom
operator<< with printing hex values of bytes. Are you suggesting
interleaving

std::cout << complex_object;
printf("%x",byte);

and hope that buffering makes that OK?

Alternatively, you may want to serialise some bytes to a
std::stringstream or serialise some bytes to a stream provided by a
library user as a std::eek:stream& arguments, or to a file which has been
opened as an std::fstream ... or ... or ...

fprintf is fine, if you're writing to a C-style FILE*.
It's useless for anything else, and there are *plenty* of anything-
elses.

The standard stream-formatting API is an bloody disaster area, so full
of gotchas and weirdness as to be almost-unusable. Boost::Format is
the solution.
 
J

Jorgen Grahn

Have you considered that 0xFF is outside the range a signed 'char' is
guaranteed to represent? Or is your 'char' unsigned by default? Just
checking...


Similar to "How do I put my trousers on by pulling them over my head?".

Use 'printf', it seems to suit *this particular task* better.

I tend to use

#include <iostream>
struct format_as_hex {
....
};
std::cout << format_as_hex(c);

and let 'format_as_hex' use sprintf() internally.

/Jorgen
 
I

Ian Collins

char c = 0xFF;

Q1: How do I use cout to print the variable c so that it appears at
stdout as "FF"?

char buff[3];
sprintf(buff, "%02X", c);
std::cout<< buff;

If you are afraid that char is 32 or 64 bits on some platform and might not
fit into the buffer, you can make the buffer e.g. 17 bytes long as a
precaution.

The buffer is an array of char, so it will always be big enough no
matter how big a char is (in c++ terms it is always 1).
The point is that the dreaded buffer overflows associated with
sprintf() can be avoided here easily as the output size is constrained, so
there is no reason why sprintf() could not be used if it suits the task
better.

Completely agree.
 
G

gwowen

The buffer is an array of char, so it will always be big enough no
matter how big a char is (in c++ terms it is always 1).

A char value bigger than 255 will need three (or more) char's to hold
its ascii hex representation. No matter how big a char is, once
you're representing it as an ASCII sequence of 0-9A-F, you're going to
need a string of length ~ log_16(CHAR_MAX). Just like you need 3
bytes to hold the ascii decimal representation of an 8-bit char now, "
0"-"255"
 
I

Ian Collins

A char value bigger than 255 will need three (or more) char's to hold
its ascii hex representation. No matter how big a char is, once
you're representing it as an ASCII sequence of 0-9A-F, you're going to
need a string of length ~ log_16(CHAR_MAX). Just like you need 3
bytes to hold the ascii decimal representation of an 8-bit char now, "
0"-"255"

Don't forget the the format string was "%02X"..
 
G

gwowen

Don't forget the the format string was "%02X"..

Don't forget that width specifiers are a minumum. (Another talented,
concientious, experienced C-user, and *boom* another potential
sprintf() overflow bug).

sprintf() is horrid.
 
J

Jorgen Grahn

Which is why snprintf(3c) is preferred.

You still have to decide though what to do when you have truncation.
If you ignore the error and continue that might (in some cases) be
just as bad as the sprintf() buffer overflow.

/Jorgen
 
8

88888 Dihedral

在 2012å¹´2月20日星期一UTC+8上åˆ1æ—¶24分19秒,io_x写é“:
"gwowen" <[email protected]> ha scritto nel messaggio


But sometimes you want to mix streaming objects with a custom
operator<< with printing hex values of bytes. Are you suggesting
interleaving

Well, after my carefully investigations of << and >>
, I bielive it is not so trivail in C++ to control.

For example, I have to set up bufers for a
data compressed encoder and decoder of various comprssion methods with options for fast speed RW operations or smaller sizes in the heap or the swap
files in the hd.

How do I pass the option?

Unless I design a control foarmt for the stream
or use some external methods to pass the options
to the stream operators, I can't think of better ways
in C++ stream operator reloading.

I am wondering is there other way for the >> and <<
operator reloadings.
 
8

88888 Dihedral

88888 Dihedralæ–¼ 2012å¹´2月20日星期一UTC+8下åˆ7時19分35秒寫é“:
在 2012å¹´2月20日星期一UTC+8上åˆ1æ—¶24分19秒,io_x写é“:

Well, after my carefully investigations of << and >>
, I bielive it is not so trivail in C++ to control.

For example, I have to set up bufers for a
data compressed encoder and decoder of various comprssion methods with options for fast speed RW operations or smaller sizes in the heap or the swap
files in the hd.

How do I pass the option?

Unless I design a control foarmt for the stream
or use some external methods to pass the options
to the stream operators, I can't think of better ways
in C++ stream operator reloading.

I am wondering is there other way for the >> and <<
operator reloadings.

I studied the python bit-torrent long time ago. It is easy to set up sites
to join the torrents in Python. But how to do that in C++??
 

Ask a Question

Want to reply to this thread or ask your own question?

You'll need to choose a username for the site, which only take a couple of moments. After that, you can post your question and our members will help you out.

Ask a Question

Members online

Forum statistics

Threads
474,261
Messages
2,571,041
Members
48,769
Latest member
Clifft

Latest Threads

Top