Double -> C-String conversion

Discussion in 'C++' started by Der Andere, Apr 26, 2004.

  1. Der Andere

    Der Andere Guest

    During every iteration in a loop, I need to convert a double value into a
    char*. Simple type-casting did not work, so I thought of using
    stringstreams. However, the stream would have to be *emptied* after each
    iteration (and I could not conceive of a practical way doing that).

    Cheers,
    Matthias
    --
    Für emails Anweisung in der Adresse befolgen
     
    Der Andere, Apr 26, 2004
    #1
    1. Advertising

  2. Der Andere

    Rolf Magnus Guest

    Der Andere wrote:

    > During every iteration in a loop, I need to convert a double value
    > into a char*. Simple type-casting did not work, so I thought of using
    > stringstreams.


    Sounds as if you want a string representation of your double. A char* is
    not a string. It's a pointer to char, nothing less, nothing more.

    > However, the stream would have to be *emptied* after each iteration
    > (and I could not conceive of a practical way doing that).


    Do the following:

    thestream.str("");
     
    Rolf Magnus, Apr 26, 2004
    #2
    1. Advertising

  3. Der Andere

    Karthik Guest

    Der Andere wrote:

    > During every iteration in a loop, I need to convert a double value into a
    > char*. Simple type-casting did not work, so I thought of using
    > stringstreams. However, the stream would have to be *emptied* after each
    > iteration (and I could not conceive of a practical way doing that).


    How about using sprintf ?

    sprintf(p, "%lf", doubleval);
    // Remember to allocate memory to p before you do this.

    HTH
    >
    > Cheers,
    > Matthias
    > --
    > Für emails Anweisung in der Adresse befolgen
    >
    >



    --
    Karthik

    ------

    Human Beings please 'removeme' for my email.
     
    Karthik, Apr 26, 2004
    #3
  4. Der Andere

    Der Andere Guest

    > > During every iteration in a loop, I need to convert a double value
    > > into a char*. Simple type-casting did not work, so I thought of using
    > > stringstreams.

    >
    > Sounds as if you want a string representation of your double. A char* is
    > not a string. It's a pointer to char, nothing less, nothing more.


    C-string, yes. I thought I could indicate a c-string with char *: Would
    char[] be better?

    > > However, the stream would have to be *emptied* after each iteration
    > > (and I could not conceive of a practical way doing that).

    >
    > Do the following:
    >
    > thestream.str("");


    It works now, cheers :)

    Matthias
     
    Der Andere, Apr 26, 2004
    #4
  5. Der Andere

    Jeff Schwab Guest

    Rolf Magnus wrote:
    > Der Andere wrote:
    >
    >
    >>During every iteration in a loop, I need to convert a double value
    >>into a char*. Simple type-casting did not work, so I thought of using
    >>stringstreams.

    >
    >
    > Sounds as if you want a string representation of your double. A char* is
    > not a string. It's a pointer to char, nothing less, nothing more.
    >
    >
    >>However, the stream would have to be *emptied* after each iteration
    >>(and I could not conceive of a practical way doing that).

    >
    >
    > Do the following:
    >
    > thestream.str("");


    Alternatively:

    thestream.str( ).clear( );
     
    Jeff Schwab, Apr 26, 2004
    #5
  6. Der Andere

    Rolf Magnus Guest

    Jeff Schwab wrote:

    > Rolf Magnus wrote:
    >> Der Andere wrote:
    >>
    >>
    >>>During every iteration in a loop, I need to convert a double value
    >>>into a char*. Simple type-casting did not work, so I thought of using
    >>>stringstreams.

    >>
    >>
    >> Sounds as if you want a string representation of your double. A char*
    >> is not a string. It's a pointer to char, nothing less, nothing more.
    >>
    >>
    >>>However, the stream would have to be *emptied* after each iteration
    >>>(and I could not conceive of a practical way doing that).

    >>
    >>
    >> Do the following:
    >>
    >> thestream.str("");

    >
    > Alternatively:
    >
    > thestream.str( ).clear( );


    According to Stroustrup, this shouldn't empty the stream, because str()
    returns a copy of the string.
     
    Rolf Magnus, Apr 26, 2004
    #6
  7. Der Andere

    Rolf Magnus Guest

    Der Andere wrote:

    >> > During every iteration in a loop, I need to convert a double value
    >> > into a char*. Simple type-casting did not work, so I thought of
    >> > using stringstreams.

    >>
    >> Sounds as if you want a string representation of your double. A char*
    >> is not a string. It's a pointer to char, nothing less, nothing more.

    >
    > C-string, yes. I thought I could indicate a c-string with char *:
    > Would char[] be better?


    No. Actually, char[] is only allowed if used as a paremter. I just
    wanted to clarify that char* isn't C's string type. C doesn't have a
    string type. Therefore, there is no built-in way to convert something
    into a string, and that explains why casting to char* doesn't do what
    you want.
     
    Rolf Magnus, Apr 26, 2004
    #7
  8. Der Andere

    Jack Klein Guest

    On Sun, 25 Apr 2004 16:37:02 -0700, Karthik
    <> wrote in comp.lang.c++:

    > Der Andere wrote:
    >
    > > During every iteration in a loop, I need to convert a double value into a
    > > char*. Simple type-casting did not work, so I thought of using
    > > stringstreams. However, the stream would have to be *emptied* after each
    > > iteration (and I could not conceive of a practical way doing that).

    >
    > How about using sprintf ?


    That's a possibility but...

    > sprintf(p, "%lf", doubleval);


    In all versions of the ISO C standard prior to 1999, including the
    1995 version that the C++ standard inherits from, "%lf" is an
    ill-formed conversion specifier for the *printf() functions and
    produces undefined behavior.

    There is no need for separate conversion specifiers for float and
    double in *printf, as floats are always promoted to double as is the
    case for all optional parameters to all variadic functions in C and
    C++.

    The 1999 update to the C standard made the 'l' length modifier a no-op
    with the all floating point conversion specifiers, but this is not
    part of the current C++ standard. The "%lf" *printf conversion
    specifier causes undefined behavior in C++.

    > // Remember to allocate memory to p before you do this.
    >
    > HTH
    > >
    > > Cheers,
    > > Matthias


    --
    Jack Klein
    Home: http://JK-Technology.Com
    FAQs for
    comp.lang.c http://www.eskimo.com/~scs/C-faq/top.html
    comp.lang.c++ http://www.parashift.com/c -faq-lite/
    alt.comp.lang.learn.c-c++
    http://www.contrib.andrew.cmu.edu/~ajo/docs/FAQ-acllc.html
     
    Jack Klein, Apr 26, 2004
    #8
  9. "Jeff Schwab" <> wrote in message
    news:...
    > Rolf Magnus wrote:
    > > Der Andere wrote:
    > >
    > >
    > >>During every iteration in a loop, I need to convert a double value
    > >>into a char*. Simple type-casting did not work, so I thought of using
    > >>stringstreams.

    > >
    > >
    > > Sounds as if you want a string representation of your double. A char* is
    > > not a string. It's a pointer to char, nothing less, nothing more.
    > >
    > >
    > >>However, the stream would have to be *emptied* after each iteration
    > >>(and I could not conceive of a practical way doing that).

    > >
    > >
    > > Do the following:
    > >
    > > thestream.str("");

    >
    > Alternatively:
    >
    > thestream.str( ).clear( );


    That doesn't work. It clears the error flags of the stream. That's what
    clear does for any stream, it has nothing to do with emptying a string
    stream.

    john
     
    John Harrison, Apr 26, 2004
    #9
  10. "Jack Klein" <> wrote in message
    news:...
    > On Sun, 25 Apr 2004 16:37:02 -0700, Karthik
    > <> wrote in comp.lang.c++:
    >
    > > Der Andere wrote:
    > >
    > > > During every iteration in a loop, I need to convert a double value

    into a
    > > > char*. Simple type-casting did not work, so I thought of using
    > > > stringstreams. However, the stream would have to be *emptied* after

    each
    > > > iteration (and I could not conceive of a practical way doing that).

    > >
    > > How about using sprintf ?

    >
    > That's a possibility but...
    >
    > > sprintf(p, "%lf", doubleval);

    >
    > In all versions of the ISO C standard prior to 1999, including the
    > 1995 version that the C++ standard inherits from, "%lf" is an
    > ill-formed conversion specifier for the *printf() functions and
    > produces undefined behavior.
    >


    How did this misunderstanding become so widespread? So widespread in fact
    that the C standard committee felt obliged to change the standard.

    john
     
    John Harrison, Apr 26, 2004
    #10
  11. Rolf Magnus <> wrote in message
    news:c6hld1$e3j$05$-online.com...

    > No. Actually, char[] is only allowed if used as a paremter. I just
    > wanted to clarify that char* isn't C's string type. C doesn't have a
    > string type. Therefore, there is no built-in way to convert something
    > into a string, and that explains why casting to char* doesn't do what
    > you want.



    Nor does C++ have a string type. It has a library template instantiation
    called. C has a string concept, it is not an intrinsic type just as C++'s is
    not. That C string, and you will find the term defined in the C standard, is
    an array or array-like region of char terminated by a null character.

    To convert a double to such a string, the sprintf() function can be used. I
    would recommend using C++ strstreams instead.


    Brian Rodenborn
     
    Brian Rodenborn, Apr 26, 2004
    #11
  12. "John Harrison" <> wrote in message
    news:c6i5q4$c6ls2$-berlin.de...
    > > > sprintf(p, "%lf", doubleval);

    > >
    > > In all versions of the ISO C standard prior to 1999, including the
    > > 1995 version that the C++ standard inherits from, "%lf" is an
    > > ill-formed conversion specifier for the *printf() functions and
    > > produces undefined behavior.

    >
    > How did this misunderstanding become so widespread? So widespread in fact
    > that the C standard committee felt obliged to change the standard.


    Because when you want to read a double value, you use:
    sscanf(p, "%lf", &doubleval); // for float: ... "%f", &floatval)

    The implicit conversion of variadic function parameters from
    float to double does not apply to pointers, as used in scan functions.

    Given that the implicit conversion exists in printf (the parameters
    received are always double, never float), it kind of makes sense
    that %f and %lf be made equivalent, or even that %lf be the primary
    choice. (But as Jack pointed out, %lf is formally UB in C++98 and C90).


    Regards,
    Ivan
    --
    http://ivan.vecerina.com/contact/?subject=NG_POST <- e-mail contact form
     
    Ivan Vecerina, Apr 26, 2004
    #12
  13. Der Andere

    Jeff Schwab Guest

    Rolf Magnus wrote:
    > Jeff Schwab wrote:
    >
    >
    >>Rolf Magnus wrote:
    >>
    >>>Der Andere wrote:
    >>>
    >>>
    >>>
    >>>>During every iteration in a loop, I need to convert a double value
    >>>>into a char*. Simple type-casting did not work, so I thought of using
    >>>>stringstreams.
    >>>
    >>>
    >>>Sounds as if you want a string representation of your double. A char*
    >>>is not a string. It's a pointer to char, nothing less, nothing more.
    >>>
    >>>
    >>>
    >>>>However, the stream would have to be *emptied* after each iteration
    >>>>(and I could not conceive of a practical way doing that).
    >>>
    >>>
    >>>Do the following:
    >>>
    >>>thestream.str("");

    >>
    >>Alternatively:
    >>
    >> thestream.str( ).clear( );

    >
    >
    > According to Stroustrup, this shouldn't empty the stream, because str()
    > returns a copy of the string.


    Whoops! You're absolutely right.
     
    Jeff Schwab, Apr 26, 2004
    #13
  14. Der Andere

    Jeff Schwab Guest

    John Harrison wrote:
    > "Jeff Schwab" <> wrote in message
    > news:...
    >
    >>Rolf Magnus wrote:
    >>
    >>>Der Andere wrote:
    >>>
    >>>
    >>>
    >>>>During every iteration in a loop, I need to convert a double value
    >>>>into a char*. Simple type-casting did not work, so I thought of using
    >>>>stringstreams.
    >>>
    >>>
    >>>Sounds as if you want a string representation of your double. A char* is
    >>>not a string. It's a pointer to char, nothing less, nothing more.
    >>>
    >>>
    >>>
    >>>>However, the stream would have to be *emptied* after each iteration
    >>>>(and I could not conceive of a practical way doing that).
    >>>
    >>>
    >>>Do the following:
    >>>
    >>>thestream.str("");

    >>
    >>Alternatively:
    >>
    >> thestream.str( ).clear( );

    >
    >
    > That doesn't work. It clears the error flags of the stream. That's what
    > clear does for any stream, it has nothing to do with emptying a string
    > stream.


    No, John, you've mistaken the clear() method of the stream for the
    clear() method of the underlying stream. The str() method here returns
    a string, not a stream.

    This is a great example of why unnecessary abbreviations are such a bad
    idea when choosing identifiers.
     
    Jeff Schwab, Apr 26, 2004
    #14
  15. Der Andere

    Jeff Schwab Guest

    John Harrison wrote:
    > "Jeff Schwab" <> wrote in message
    > news:...
    >
    >>Rolf Magnus wrote:
    >>
    >>>Der Andere wrote:
    >>>
    >>>
    >>>
    >>>>During every iteration in a loop, I need to convert a double value
    >>>>into a char*. Simple type-casting did not work, so I thought of using
    >>>>stringstreams.
    >>>
    >>>
    >>>Sounds as if you want a string representation of your double. A char* is
    >>>not a string. It's a pointer to char, nothing less, nothing more.
    >>>
    >>>
    >>>
    >>>>However, the stream would have to be *emptied* after each iteration
    >>>>(and I could not conceive of a practical way doing that).
    >>>
    >>>
    >>>Do the following:
    >>>
    >>>thestream.str("");

    >>
    >>Alternatively:
    >>
    >> thestream.str( ).clear( );

    >
    >
    > That doesn't work. It clears the error flags of the stream. That's what
    > clear does for any stream, it has nothing to do with emptying a string
    > stream.
    >
    > john
    >
    >


    No, John, you're wrong. You've mistaken the clear() method of the
    stream for the clear() method of the underlying stream. The str()
    method here returns a string, not a stream. This does clear the string
    representation of the stream's contents, not the stream's error flags.
    (Unfortunately, as Rolf pointed out, it clears only a temporary copy of
    the string, so the stream is unaffected. I wonder, why isnt the
    temporary string const?)

    This is a great example of why unnecessary abbreviations are such a bad
    idea when choosing identifiers.
     
    Jeff Schwab, Apr 26, 2004
    #15
  16. Der Andere

    Jack Klein Guest

    On Mon, 26 Apr 2004 06:13:44 +0100, "John Harrison"
    <> wrote in comp.lang.c++:

    >
    > "Jack Klein" <> wrote in message
    > news:...
    > > On Sun, 25 Apr 2004 16:37:02 -0700, Karthik
    > > <> wrote in comp.lang.c++:
    > >
    > > > Der Andere wrote:
    > > >
    > > > > During every iteration in a loop, I need to convert a double value

    > into a
    > > > > char*. Simple type-casting did not work, so I thought of using
    > > > > stringstreams. However, the stream would have to be *emptied* after

    > each
    > > > > iteration (and I could not conceive of a practical way doing that).
    > > >
    > > > How about using sprintf ?

    > >
    > > That's a possibility but...
    > >
    > > > sprintf(p, "%lf", doubleval);

    > >
    > > In all versions of the ISO C standard prior to 1999, including the
    > > 1995 version that the C++ standard inherits from, "%lf" is an
    > > ill-formed conversion specifier for the *printf() functions and
    > > produces undefined behavior.
    > >

    >
    > How did this misunderstanding become so widespread? So widespread in fact
    > that the C standard committee felt obliged to change the standard.
    >
    > john


    How did "void main()" become so widespread, as it is considerably more
    so than "%lf"?

    The real problem is the lack of symmetry between the *printf and
    *scanf families. Both "%f" and "%lf" are required for the *scanf
    family of functions, which receive a pointer to the destination type
    and therefore can convert to both float and double.

    Given that, it would have been better to accept "%lf" in printf all
    along, and many compilers do as an extension, but there are also some
    (no idea on relative percentage) that choke on it, as the standard
    entitles them to do.

    --
    Jack Klein
    Home: http://JK-Technology.Com
    FAQs for
    comp.lang.c http://www.eskimo.com/~scs/C-faq/top.html
    comp.lang.c++ http://www.parashift.com/c -faq-lite/
    alt.comp.lang.learn.c-c++
    http://www.contrib.andrew.cmu.edu/~ajo/docs/FAQ-acllc.html
     
    Jack Klein, Apr 27, 2004
    #16
  17. Der Andere

    L Russ Guest

    "Der Andere" <> wrote in message news:<c6hh15$ccm$02$-online.com>...
    > During every iteration in a loop, I need to convert a double value into a
    > char*. Simple type-casting did not work, so I thought of using
    > stringstreams. However, the stream would have to be *emptied* after each
    > iteration (and I could not conceive of a practical way doing that).


    I'm not sure you need to "empty" the stream after each iteration,
    maybe just construct a new one.

    Maybe like this
    ----------------------------
    #include <iostream>
    #include <sstream>
    int main() {
    static const double x[] = { 0.5, 123.456789, -99.2 };
    for(int i=0; i<sizeof(x)/sizeof(x[0]); i++) {
    std::eek:stringstream ox;
    ox << x;
    std::cout
    << i << " " // number of item
    << x << " " // raw item
    << ox.str() << " " // item as string
    << ox.str().c_str() // item as char *
    << std::endl;
    }
    return 0;
    }
    ----------------------------
    The output is:

    0 0.5 0.5 0.5
    1 123.457 123.457 123.457
    2 -99.2 -99.2 -99.2

    HTH
    LR
     
    L Russ, Apr 27, 2004
    #17
    1. Advertising

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

It takes just 2 minutes to sign up (and it's free!). Just click the sign up button to choose a username and then you can ask your own questions on the forum.
Similar Threads
  1. Marco Traverso
    Replies:
    5
    Views:
    15,133
    Marco Traverso
    Dec 7, 2003
  2. kaede
    Replies:
    1
    Views:
    497
    David Hilsee
    Sep 4, 2004
  3. Sydex
    Replies:
    12
    Views:
    6,506
    Victor Bazarov
    Feb 17, 2005
  4. AviraM
    Replies:
    2
    Views:
    6,386
    Manish Pandit
    Sep 28, 2006
  5. J.M.
    Replies:
    5
    Views:
    785
Loading...

Share This Page