Re: Issues with close() and close_enough()

Posted by Luigi Ballabio on
URL: http://quantlib.414.s1.nabble.com/Issues-with-close-and-close-enough-tp8064p8066.html

Simon,
    I think the behavior with 0 was intentional in the original Knuth
algorithm (which I can't seem to find though).  You're probably right
though, it's surprising and we should probably change it.  I'm not
sure about checking for nulls.  Maybe only in debug mode?

Luigi

On Fri, Jun 1, 2012 at 4:37 PM, Simon Shakeshaft
<[hidden email]> wrote:

> Hi,
>
> I believe there is an issue in the close() function in comparison.hpp
>
> e.g. close(0.0, std::numeric_limits<double>::min(), 42) returns false.
>
>
>
> The issue is here:
>         return diff <= tolerance*std::fabs(x) &&
>                diff <= tolerance*std::fabs(y);
>
> if x (or y) is zero then this reduces to
>
>  return diff <= 0 &&
>                diff <= tolerance*std::fabs(y)
>
> which is true iif y == 0 (tolerance > 0).
>
> [yes, there are other issues when comparing small FP numbers as well…]
>
> I've attached a suggested patch. The patch also checks for Null<Real> being
> passed and the function returns false in the case either, or both arguments
> are Null<Real>, although it’s possible that a throw may be better (see later
> useage.)
>
> There is also a direct equality test to deal with +/-infinity FP
> representations.
>
> A quick wildcard search through the project files shows:
>
>
> Find all "close(*0*)", Wildcards, Subfolders, Find Results 1, "Current
> Project"
>   \QuantLib-1.2\ql\experimental\callablebonds\callablebond.cpp(126):
> bool isZeroCouponBond = (coupons.size() == 1 && close(coupons[0], 0.0));
>   \QuantLib-1.2\ql\math\solvers1d\bisection.hpp(65):                if
> (std::fabs(dx) < xAccuracy || (close(fMid, 0.0)))
>   \QuantLib-1.2\ql\math\solvers1d\brent.hpp(74):                if
> (std::fabs(xMid) <= xAcc1 || (close(froot, 0.0)))
>   \QuantLib-1.2\ql\math\solvers1d\falseposition.hpp(77):                if
> (std::fabs(del) < xAccuracy || (close(froot, 0.0)))
>   \QuantLib-1.2\ql\math\solvers1d\ridder.hpp(63):                if
> (close(s, 0.0))
>   \QuantLib-1.2\ql\math\solvers1d\ridder.hpp(75):                if
> (close(froot, 0.0))
>   \QuantLib-1.2\ql\math\solvers1d\secant.hpp(69):                if
> (std::fabs(dx) < xAccuracy || (close(froot, 0.0)))
>   \QuantLib-1.2\ql\math\solver1d.hpp(102):            if (close(fxMax_,0.0))
>   \QuantLib-1.2\ql\math\solver1d.hpp(104):            else if (close(fxMax_,
> 0.0)) {
>   \QuantLib-1.2\ql\math\solver1d.hpp(118):                    if
> (close(fxMin_, 0.0))
>   \QuantLib-1.2\ql\math\solver1d.hpp(120):                    if
> (close(fxMax_, 0.0))
>   \QuantLib-1.2\ql\math\solver1d.hpp(189):            if (close(fxMin_,
> 0.0))
>   \QuantLib-1.2\ql\math\solver1d.hpp(193):            if (close(fxMax_,
> 0.0))
>
> \QuantLib-1.2\ql\methods\finitedifferences\tridiagonaloperator.cpp(101):
> QL_REQUIRE(!close(bet, 0.0),
>
> \QuantLib-1.2\ql\methods\finitedifferences\tridiagonaloperator.cpp(108):
> QL_ENSURE(!close(bet, 0.0), "division by zero");
>
> \QuantLib-1.2\ql\models\marketmodels\correlations\expcorrelations.cpp(97):
> if (close(gamma,1.0)) {
>   \QuantLib-1.2\ql\pricingengines\blackcalculator.cpp(80):            if
> (close(strike_, 0.0)) {
>   \QuantLib-1.2\ql\pricingengines\blackcalculator.cpp(297):        if
> (close(maturity, 0.0)) return 0.0;
>   Matching lines: 18    Matching files: 10    Total files searched: 1799
>
> and also
> Find all "close(*null*)", Wildcards, Subfolders, Find Results 1, "Current
> Project"
>   C:\SharedLibs\QuantLib-1.2\ql\index.hpp(99):                missingFixing=
> forceOverwrite || close(currentValue,nullValue);
>   [nullValue = Null<Real>();]
>
>   Matching lines: 1    Matching files: 1    Total files searched: 1799
>
> The last one can probably be corrected as missingFixing= forceOverwrite ||
> (currentValue==Null<Real>()); [and remove the declaration of nullValue.]
>
> Best Regards,
> Simon
>
>
> ------------------------------------------------------------------------------
> Live Security Virtual Conference
> Exclusive live event will cover all the ways today's security and
> threat landscape has changed and how IT managers can respond. Discussions
> will include endpoint security, mobile security and the latest in malware
> threats. http://www.accelacomm.com/jaw/sfrnl04242012/114/50122263/
> _______________________________________________
> QuantLib-users mailing list
> [hidden email]
> https://lists.sourceforge.net/lists/listinfo/quantlib-users
>

------------------------------------------------------------------------------
Live Security Virtual Conference
Exclusive live event will cover all the ways today's security and
threat landscape has changed and how IT managers can respond. Discussions
will include endpoint security, mobile security and the latest in malware
threats. http://www.accelacomm.com/jaw/sfrnl04242012/114/50122263/
_______________________________________________
QuantLib-users mailing list
[hidden email]
https://lists.sourceforge.net/lists/listinfo/quantlib-users