Tcl Library Source Code

View Ticket
Login
Ticket UUID: 3309165
Title: math::bigfloat::isInt returns 1 on non-integers
Type: Bug Version: None
Submitter: blacksqr Created on: 2011-05-30 07:17:51
Subsystem: math Assigned To:
Priority: 5 Medium Severity: Minor
Status: Closed Last Modified: 2014-09-21 13:17:17
Resolution: Fixed Closed By:
    Closed on:
Description:
Tcl 8.5
math::bigfloat version 2.0.1

The procedure math::bigfloat::isInt performs a very naive check to distinguish BigFloats from integers, but the check isn't nearly comprehensive enough to cover all or even most cases.  The doc states that the proc should be able to distinguish standard Tcl 8.5 integers from other values.  But note for example:

% isInt 2.0
1
% isInt 0.5
1
% isInt 1/2
1
% isInt [expr exp(1)]
1
% isInt i
1
% isInt HAM_SANDWICH
1

A better implementation might be something like:

proc isInt {n} {
if {[catch {set n [expr abs($n)]}]} {return 0}
if {[string first . $n] > -1} {return 0}
return 1
}
User Comments: arjenmarkus added on 2014-09-21 13:17:17:
Fixed this bug - the original implementation simply checked if it was a single string, nothing more.

To avoid the overhead of converting a number to a string, I have chosen the following implementation:

proc ::math::bigfloat::isInt {n} {
    set rc [catch {
        expr {$n%2}
    }]
    return [expr {$rc == 0}]
}

blacksqr added on 2011-12-01 12:03:16:
Here's a one-liner:

proc isInt {n} {expr ![catch {format %x $n}]}