[BACK]Return to ismpf.cc CVS log [TXT][DIR] Up to [local] / OpenXM_contrib / gmp / cxx

Annotation of OpenXM_contrib/gmp/cxx/ismpf.cc, Revision 1.1.1.1

1.1       ohara       1: /* operator>> -- C++-style input of mpf_t.
                      2:
                      3: Copyright 2001, 2002 Free Software Foundation, Inc.
                      4:
                      5: This file is part of the GNU MP Library.
                      6:
                      7: The GNU MP Library is free software; you can redistribute it and/or modify
                      8: it under the terms of the GNU Lesser General Public License as published by
                      9: the Free Software Foundation; either version 2.1 of the License, or (at your
                     10: option) any later version.
                     11:
                     12: The GNU MP Library is distributed in the hope that it will be useful, but
                     13: WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
                     14: or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU Lesser General Public
                     15: License for more details.
                     16:
                     17: You should have received a copy of the GNU Lesser General Public License
                     18: along with the GNU MP Library; see the file COPYING.LIB.  If not, write to
                     19: the Free Software Foundation, Inc., 59 Temple Place - Suite 330, Boston,
                     20: MA 02111-1307, USA. */
                     21:
                     22: #include "config.h"
                     23:
                     24: #include <cctype>
                     25: #include <iostream>
                     26: #include <string>
                     27:
                     28: #if HAVE_LOCALE_H
                     29: #include <locale.h>    /* for localeconv */
                     30: #endif
                     31:
                     32: #include "gmp.h"
                     33: #include "gmp-impl.h"
                     34:
                     35: using namespace std;
                     36:
                     37:
                     38: /* Perhaps the decimal point should be taken from the C++ <locale> stuff,
                     39:    but that doesn't exist in g++ 2.95.x.  In any case, using plain C
                     40:    localeconv will ensure we parse exactly what mpf_set_str will expect, and
                     41:    what the current operator<< implementation produces.  */
                     42:
                     43: istream &
                     44: operator>> (istream &i, mpf_ptr f)
                     45: {
                     46:   int base;
                     47:   char c = 0;
                     48:   string s;
                     49:   bool ok = false;
                     50:
                     51:   i.get(c); // start reading
                     52:
                     53:   if (i.flags() & ios::skipws) // skip initial whitespace
                     54:     while (isspace(c) && i.get(c))
                     55:       ;
                     56:
                     57:   if (c == '-' || c == '+') // sign
                     58:     {
                     59:       if (c == '-')
                     60:        s = "-";
                     61:       i.get(c);
                     62:
                     63:       while (isspace(c) && i.get(c)) // skip whitespace
                     64:        ;
                     65:     }
                     66:
                     67:   base = 10; // octal/hex floats currently unsupported
                     68:   __gmp_istream_set_digits(s, i, c, ok, base); // read the number
                     69:
                     70: #if HAVE_LOCALECONV
                     71:   const char  *point = localeconv()->decimal_point;
                     72:   if (c == *point) // radix point
                     73:     {
                     74:       for (;;)
                     75:         {
                     76:           s += c;
                     77:           i.get(c);
                     78:           point++;
                     79:           if (*point == '\0')
                     80:             break;
                     81:           if (c != *point)
                     82:             goto fail;
                     83:         }
                     84:       __gmp_istream_set_digits(s, i, c, ok, base); // read the mantissa
                     85:     }
                     86: #else
                     87:   if (c == '.') // radix point
                     88:     {
                     89:       s += '.';
                     90:       i.get(c);
                     91:       __gmp_istream_set_digits(s, i, c, ok, base); // read the mantissa
                     92:     }
                     93: #endif
                     94:
                     95:   if (ok && (c == 'e' || c == 'E' || c == '@')) // exponent
                     96:     {
                     97:       s += c;
                     98:       i.get(c);
                     99:       ok = false; // exponent is mandatory
                    100:
                    101:       if (c == '-' || c == '+') // sign
                    102:        {
                    103:          s += c;
                    104:          i.get(c);
                    105:
                    106:          while (isspace(c) && i.get(c)) // skip whitespace
                    107:            ;
                    108:        }
                    109:
                    110:       __gmp_istream_set_digits(s, i, c, ok, base); // read the exponent
                    111:     }
                    112:
                    113:   if (i.good()) // last character read was non-numeric
                    114:     i.putback(c);
                    115:   else if (i.eof() && ok) // stopped just before eof
                    116:     i.clear();
                    117:
                    118:   if (ok)
                    119:     mpf_set_str(f, s.c_str(), base); // extract the number
                    120:   else
                    121:     {
                    122:     fail:
                    123:       i.setstate(ios::failbit); // read failed
                    124:     }
                    125:
                    126:   return i;
                    127: }

FreeBSD-CVSweb <freebsd-cvsweb@FreeBSD.org>