Paul J. Lucas has proposed merging lp:~paul-lucas/zorba/bug-1090089 into lp:zorba.
Commit message: Rewrote decimal reduction code -- fixes rounding and FOTS distinct-values tests. Requested reviews: Paul J. Lucas (paul-lucas) Related bugs: Bug #1090089 in Zorba: "fn-distinct-values different results from test" https://bugs.launchpad.net/zorba/+bug/1090089 For more details, see: https://code.launchpad.net/~paul-lucas/zorba/bug-1090089/+merge/163085 Rewrote decimal reduction code -- fixes rounding and FOTS distinct-values tests. -- https://code.launchpad.net/~paul-lucas/zorba/bug-1090089/+merge/163085 Your team Zorba Coders is subscribed to branch lp:zorba.
=== modified file 'src/zorbatypes/decimal.cpp' --- src/zorbatypes/decimal.cpp 2013-05-05 03:16:33 +0000 +++ src/zorbatypes/decimal.cpp 2013-05-09 05:21:28 +0000 @@ -73,98 +73,62 @@ } /** - * Remove trailing .99999 or .000001. - * Find four or five consecutive 9 or 0 after decimal point and eliminate them. + * Removes trailing .999 or .001. */ void Decimal::reduce( char *s ) { - char *dot = strrchr( s, '.' ); - if ( !dot ) // not a floating point number + if ( !strrchr( s, '.' ) ) // not a floating-point number return; - bool has_e = false; - char *e = strrchr( s, 'E' ); - if ( !e ) - e = strrchr( s, 'e' ); - if ( !e ) - e = s + strlen( s ); - else - has_e = true; - - char *digits = e - 1; - for ( int pos = (int)(digits - dot); pos > 8; --pos, --digits ) { - if ( *digits == '9' ) { - if ( digits[-1] == '9' && digits[-2] == '9' && digits[-3] == '9' ) { - if ( ascii::is_digit( digits[1] ) && digits[1] >= '5' ) - digits -= 4; - else if ( digits[-4] == '9' ) - digits -= 5; - else - continue; - - // now add 1 to remaining digits - char *last_digit = digits; - while ( digits >= s ) { - if ( digits[0] == '.' ) { - // skip - } else if ( digits[0] == '9' ) { - digits[0] = '0'; - if ( last_digit == digits ) - --last_digit; - } else { - if ( ascii::is_digit( digits[0] ) ) - digits[0]++; - break; - } - --digits; - } - if ( last_digit[0] != '.' ) - ++last_digit; - else if ( has_e ) { - last_digit[1] = '0'; - last_digit += 2; - } - if ( digits < s || !ascii::is_digit( digits[0] ) ) { - memmove( s + 1, s, last_digit - s ); - ++last_digit; - if ( ascii::is_digit( s[0] ) ) - s[0] = '1'; - else - s[1] = '1'; - if ( has_e ) { // increment the exponent - ++dot; - dot[0] = dot[-1]; - dot[-1] = '.'; - sprintf( e + 1, "%d", atoi( e + 1 ) + 1 ); - --last_digit; - } - } - int const e_len = strlen( e ); - memmove( last_digit, e, e_len ); - last_digit[ e_len ] = 0; - break; - } - } else if ( *digits == '0' ) { - if ( digits[-1] == '0' && digits[-2] == '0' && digits[-3] == '0' ) { - if ( ascii::is_digit( digits[1] ) && digits[1] < '5' ) - digits -= 4; - else if ( digits[-4] == '0' ) - digits -= 5; - else - continue; - while ( *digits == '0' ) - --digits; - if ( *digits != '.' ) - ++digits; - else if ( has_e ) { - digits[1] = '0'; - digits += 2; - } - int const e_len = strlen( e ); - memmove( digits, e, e_len ); - digits[ e_len ] = '\0'; - break; - } - } + char *e = strpbrk( s, "eE" ); + if ( !e ) + e = s + strlen( s ); // eliminates special-case + + char *digit = e - 1; + switch ( *digit ) { + case '0': // trim trailing zeros + while ( *digit == '0' ) + *digit-- = '\0'; + if ( *digit == '.' ) + *digit = '\0'; + break; + case '1': + int zeros; + for ( zeros = 0; *--digit == '0'; ++zeros ) + ; + if ( zeros >= 3 ) // this seems arbitrary + digit[ *digit != '.' ] = '\0'; + break; + case '9': + int nines; + for ( nines = 1; *--digit == '9'; ++nines ) + ; + if ( nines > 1 ) { + if ( *digit != '.' ) { // 123.4...99... + ++digit[0]; + ++digit; + // slide to the left: 123.4...99...[E12] => 123.4...[E12] + memmove( digit, digit + nines, strlen( e ) + 1 ); + } else { // 123.99... + *digit-- = '\0'; + char const *const first = *s == '-' ? s + 1 : s; + while ( true ) { + if ( *digit == '9' ) { + *digit = '0'; + if ( digit == first ) { + // slide to the right to insert a leading '1' + memmove( digit + 1, digit, strlen( digit ) + 1 ); + *digit = '1'; + break; + } + --digit; + } else { + ++digit[0]; + break; + } + } + } + } + break; } } === modified file 'src/zorbatypes/floatimpl.cpp' --- src/zorbatypes/floatimpl.cpp 2013-05-04 17:29:21 +0000 +++ src/zorbatypes/floatimpl.cpp 2013-05-09 05:21:28 +0000 @@ -351,11 +351,7 @@ return "0"; if ( isNegZero() ) return "-0"; - - // TODO: make xs_int - char buf[174]; - sprintf( buf, "%d", (int)value_ ); - return buf; + return ztd::to_string( static_cast<long long>( value_ ) ); } template<typename F> @@ -379,9 +375,9 @@ #if 1 // This is the "spec" implementation, i.e., it is an exact application of // the spec in http://www.w3.org/TR/xpath-functions/#casting - MAPM decimal_mapm( value_ ); - decimal_mapm = decimal_mapm.round( precision_ ); - return Decimal::toString( decimal_mapm, isNegZero(), max_precision() ); + MAPM temp( value_ ); + temp = temp.round( precision_ ); + return Decimal::toString( temp, isNegZero(), precision_ ); #else std::stringstream stream; stream.precision(7); === modified file 'src/zorbatypes/integer.cpp' --- src/zorbatypes/integer.cpp 2013-05-07 00:39:46 +0000 +++ src/zorbatypes/integer.cpp 2013-05-09 05:21:28 +0000 @@ -19,7 +19,6 @@ // standard #include <cerrno> #include <cstdlib> -#include <sstream> // Zorba #include <zorba/internal/unique_ptr.h> @@ -38,12 +37,6 @@ /////////////////////////////////////////////////////////////////////////////// -ostream& operator<<( ostream &o, MAPM const &m ) { - unique_ptr<char[]> const buf( new char[ m.exponent() + 3 ] ); - m.toIntegerString( buf.get() ); - return o << buf.get(); -} - void integer_traits::throw_error( string const &what, bool throw_range_error ) { if ( throw_range_error ) throw range_error( what ); @@ -52,9 +45,9 @@ void integer_traits::throw_error( MAPM const &n, char const *op, bool throw_range_error ) { - ostringstream oss; - oss << n; - string const what( BUILD_STRING( oss.str(), ": not ", op, " 0" ) ); + unique_ptr<char[]> const buf( new char[ n.exponent() + 3 ] ); + n.toIntegerString( buf.get() ); + string const what( BUILD_STRING( buf.get(), ": not ", op, " 0" ) ); throw_error( what, throw_range_error ); } === modified file 'src/zorbatypes/integer.h' --- src/zorbatypes/integer.h 2013-05-07 00:39:46 +0000 +++ src/zorbatypes/integer.h 2013-05-09 05:21:28 +0000 @@ -50,8 +50,6 @@ /////////////////////////////////////////////////////////////////////////////// -std::ostream& operator<<( std::ostream&, MAPM const& ); - struct integer_traits { static int const default_value = 0; === modified file 'test/fots/CMakeLists.txt' --- test/fots/CMakeLists.txt 2013-05-08 20:14:47 +0000 +++ test/fots/CMakeLists.txt 2013-05-09 05:21:28 +0000 @@ -157,8 +157,6 @@ EXPECTED_FOTS_FAILURE (fn-available-environment-variables fn-available-environment-variables-011 0) EXPECTED_FOTS_FAILURE (fn-deep-equal K2-SeqDeepEqualFunc-36 0) EXPECTED_FOTS_FAILURE (fn-deep-equal K2-SeqDeepEqualFunc-37 0) -EXPECTED_FOTS_FAILURE (fn-distinct-values cbcl-distinct-values-002 1090089) -EXPECTED_FOTS_FAILURE (fn-distinct-values cbcl-distinct-values-002b 1090089) EXPECTED_FOTS_FAILURE (fn-environment-variable environment-variable-005 0) EXPECTED_FOTS_FAILURE (fn-environment-variable environment-variable-006 0) EXPECTED_FOTS_FAILURE (fn-environment-variable environment-variable-007 0) === added file 'test/rbkt/ExpQueryResults/zorba/numerics/xs_float-01.xml.res' --- test/rbkt/ExpQueryResults/zorba/numerics/xs_float-01.xml.res 1970-01-01 00:00:00 +0000 +++ test/rbkt/ExpQueryResults/zorba/numerics/xs_float-01.xml.res 2013-05-09 05:21:28 +0000 @@ -0,0 +1,1 @@ +1.9 === added file 'test/rbkt/ExpQueryResults/zorba/numerics/xs_float-02.xml.res' --- test/rbkt/ExpQueryResults/zorba/numerics/xs_float-02.xml.res 1970-01-01 00:00:00 +0000 +++ test/rbkt/ExpQueryResults/zorba/numerics/xs_float-02.xml.res 2013-05-09 05:21:28 +0000 @@ -0,0 +1,1 @@ +2 === added file 'test/rbkt/ExpQueryResults/zorba/numerics/xs_float-03.xml.res' --- test/rbkt/ExpQueryResults/zorba/numerics/xs_float-03.xml.res 1970-01-01 00:00:00 +0000 +++ test/rbkt/ExpQueryResults/zorba/numerics/xs_float-03.xml.res 2013-05-09 05:21:28 +0000 @@ -0,0 +1,1 @@ +1.6 === added file 'test/rbkt/ExpQueryResults/zorba/numerics/xs_float-04.xml.res' --- test/rbkt/ExpQueryResults/zorba/numerics/xs_float-04.xml.res 1970-01-01 00:00:00 +0000 +++ test/rbkt/ExpQueryResults/zorba/numerics/xs_float-04.xml.res 2013-05-09 05:21:28 +0000 @@ -0,0 +1,1 @@ +10 === added file 'test/rbkt/ExpQueryResults/zorba/numerics/xs_float-05.xml.res' --- test/rbkt/ExpQueryResults/zorba/numerics/xs_float-05.xml.res 1970-01-01 00:00:00 +0000 +++ test/rbkt/ExpQueryResults/zorba/numerics/xs_float-05.xml.res 2013-05-09 05:21:28 +0000 @@ -0,0 +1,1 @@ +-1.9 === added file 'test/rbkt/ExpQueryResults/zorba/numerics/xs_float-06.xml.res' --- test/rbkt/ExpQueryResults/zorba/numerics/xs_float-06.xml.res 1970-01-01 00:00:00 +0000 +++ test/rbkt/ExpQueryResults/zorba/numerics/xs_float-06.xml.res 2013-05-09 05:21:28 +0000 @@ -0,0 +1,1 @@ +-2 === added file 'test/rbkt/ExpQueryResults/zorba/numerics/xs_float-07.xml.res' --- test/rbkt/ExpQueryResults/zorba/numerics/xs_float-07.xml.res 1970-01-01 00:00:00 +0000 +++ test/rbkt/ExpQueryResults/zorba/numerics/xs_float-07.xml.res 2013-05-09 05:21:28 +0000 @@ -0,0 +1,1 @@ +-1.6 === added file 'test/rbkt/ExpQueryResults/zorba/numerics/xs_float-08.xml.res' --- test/rbkt/ExpQueryResults/zorba/numerics/xs_float-08.xml.res 1970-01-01 00:00:00 +0000 +++ test/rbkt/ExpQueryResults/zorba/numerics/xs_float-08.xml.res 2013-05-09 05:21:28 +0000 @@ -0,0 +1,1 @@ +-10 === added file 'test/rbkt/ExpQueryResults/zorba/numerics/xs_float-09.xml.res' --- test/rbkt/ExpQueryResults/zorba/numerics/xs_float-09.xml.res 1970-01-01 00:00:00 +0000 +++ test/rbkt/ExpQueryResults/zorba/numerics/xs_float-09.xml.res 2013-05-09 05:21:28 +0000 @@ -0,0 +1,1 @@ +1 === added file 'test/rbkt/ExpQueryResults/zorba/numerics/xs_float-10.xml.res' --- test/rbkt/ExpQueryResults/zorba/numerics/xs_float-10.xml.res 1970-01-01 00:00:00 +0000 +++ test/rbkt/ExpQueryResults/zorba/numerics/xs_float-10.xml.res 2013-05-09 05:21:28 +0000 @@ -0,0 +1,1 @@ +1 === added file 'test/rbkt/ExpQueryResults/zorba/numerics/xs_float-11.xml.res' --- test/rbkt/ExpQueryResults/zorba/numerics/xs_float-11.xml.res 1970-01-01 00:00:00 +0000 +++ test/rbkt/ExpQueryResults/zorba/numerics/xs_float-11.xml.res 2013-05-09 05:21:28 +0000 @@ -0,0 +1,1 @@ +1.234 === added file 'test/rbkt/Queries/zorba/numerics/xs_float-01.xq' --- test/rbkt/Queries/zorba/numerics/xs_float-01.xq 1970-01-01 00:00:00 +0000 +++ test/rbkt/Queries/zorba/numerics/xs_float-01.xq 2013-05-09 05:21:28 +0000 @@ -0,0 +1,1 @@ +xs:float(1.899) === added file 'test/rbkt/Queries/zorba/numerics/xs_float-02.xq' --- test/rbkt/Queries/zorba/numerics/xs_float-02.xq 1970-01-01 00:00:00 +0000 +++ test/rbkt/Queries/zorba/numerics/xs_float-02.xq 2013-05-09 05:21:28 +0000 @@ -0,0 +1,1 @@ +xs:float(1.99) === added file 'test/rbkt/Queries/zorba/numerics/xs_float-03.xq' --- test/rbkt/Queries/zorba/numerics/xs_float-03.xq 1970-01-01 00:00:00 +0000 +++ test/rbkt/Queries/zorba/numerics/xs_float-03.xq 2013-05-09 05:21:28 +0000 @@ -0,0 +1,1 @@ +xs:float(1.599) === added file 'test/rbkt/Queries/zorba/numerics/xs_float-04.xq' --- test/rbkt/Queries/zorba/numerics/xs_float-04.xq 1970-01-01 00:00:00 +0000 +++ test/rbkt/Queries/zorba/numerics/xs_float-04.xq 2013-05-09 05:21:28 +0000 @@ -0,0 +1,1 @@ +xs:float(9.999) === added file 'test/rbkt/Queries/zorba/numerics/xs_float-05.xq' --- test/rbkt/Queries/zorba/numerics/xs_float-05.xq 1970-01-01 00:00:00 +0000 +++ test/rbkt/Queries/zorba/numerics/xs_float-05.xq 2013-05-09 05:21:28 +0000 @@ -0,0 +1,1 @@ +xs:float(-1.899) === added file 'test/rbkt/Queries/zorba/numerics/xs_float-06.xq' --- test/rbkt/Queries/zorba/numerics/xs_float-06.xq 1970-01-01 00:00:00 +0000 +++ test/rbkt/Queries/zorba/numerics/xs_float-06.xq 2013-05-09 05:21:28 +0000 @@ -0,0 +1,1 @@ +xs:float(-1.99) === added file 'test/rbkt/Queries/zorba/numerics/xs_float-07.xq' --- test/rbkt/Queries/zorba/numerics/xs_float-07.xq 1970-01-01 00:00:00 +0000 +++ test/rbkt/Queries/zorba/numerics/xs_float-07.xq 2013-05-09 05:21:28 +0000 @@ -0,0 +1,1 @@ +xs:float(-1.599) === added file 'test/rbkt/Queries/zorba/numerics/xs_float-08.xq' --- test/rbkt/Queries/zorba/numerics/xs_float-08.xq 1970-01-01 00:00:00 +0000 +++ test/rbkt/Queries/zorba/numerics/xs_float-08.xq 2013-05-09 05:21:28 +0000 @@ -0,0 +1,1 @@ +xs:float(-9.999) === added file 'test/rbkt/Queries/zorba/numerics/xs_float-09.xq' --- test/rbkt/Queries/zorba/numerics/xs_float-09.xq 1970-01-01 00:00:00 +0000 +++ test/rbkt/Queries/zorba/numerics/xs_float-09.xq 2013-05-09 05:21:28 +0000 @@ -0,0 +1,1 @@ +xs:float(1.0001) === added file 'test/rbkt/Queries/zorba/numerics/xs_float-10.xq' --- test/rbkt/Queries/zorba/numerics/xs_float-10.xq 1970-01-01 00:00:00 +0000 +++ test/rbkt/Queries/zorba/numerics/xs_float-10.xq 2013-05-09 05:21:28 +0000 @@ -0,0 +1,1 @@ +xs:float(1.00001) === added file 'test/rbkt/Queries/zorba/numerics/xs_float-11.xq' --- test/rbkt/Queries/zorba/numerics/xs_float-11.xq 1970-01-01 00:00:00 +0000 +++ test/rbkt/Queries/zorba/numerics/xs_float-11.xq 2013-05-09 05:21:28 +0000 @@ -0,0 +1,1 @@ +xs:float(1.2340001)
-- Mailing list: https://launchpad.net/~zorba-coders Post to : zorba-coders@lists.launchpad.net Unsubscribe : https://launchpad.net/~zorba-coders More help : https://help.launchpad.net/ListHelp