From mboxrd@z Thu Jan 1 00:00:00 1970 X-Spam-Checker-Version: SpamAssassin 3.4.4 (2020-01-24) on ip-172-31-74-118.ec2.internal X-Spam-Level: * X-Spam-Status: No, score=1.6 required=3.0 tests=BAYES_20,REPLYTO_WITHOUT_TO_CC autolearn=no autolearn_force=no version=3.4.4 Path: eternal-september.org!reader01.eternal-september.org!feeder.eternal-september.org!aioe.org!.POSTED.Ry1GfOCil8z4iThfpbQjlA.user.gioia.aioe.org!not-for-mail From: "Nasser M. Abbasi" Newsgroups: comp.lang.ada Subject: Re: Question about best practices with numerical functions Date: Sat, 4 Jul 2020 05:45:57 -0500 Organization: Aioe.org NNTP Server Message-ID: References: Reply-To: nma@12000.org NNTP-Posting-Host: Ry1GfOCil8z4iThfpbQjlA.user.gioia.aioe.org Mime-Version: 1.0 Content-Type: text/plain; charset=utf-8; format=flowed Content-Transfer-Encoding: 7bit X-Complaints-To: abuse@aioe.org User-Agent: Mozilla/5.0 (Windows NT 10.0; WOW64; rv:68.0) Gecko/20100101 Thunderbird/68.7.0 Content-Language: en-US X-Notice: Filtered by postfilter v. 0.9.2 Xref: reader01.eternal-september.org comp.lang.ada:59335 List-Id: On 7/4/2020 12:30 AM, mockturtle wrote: > Dear.all, > I have a question about the best way to manage a potential loss of precision in a numerical function. This is a doubt that came to my mind while writing a piece of software; now I solved the specific problem, but the curiosity remains. > > Let me explain. > > Recently I needed to write an implementation of the Lambert W function (is the function that given y finds x such that x*exp(x)=y). This function cannot be expressed with elementary functions and the algorithm I found basically solves the equation in an iterative way. Of course, if you fix the maximum number of iterations, it can happen that the convergence is not fast enough and you obtain a result that is potentially less precise than what you would expect. > > I was wondering how to manage such a non convergence case. Please note that I am supposing that I am writing a "general" function that could be used in many different programs. If the function was specific for a single program, then I would choose the line of action (e.g., ignore, log a warning or raise an exception) depending on the needs of the specific program. > > (Incidentally, it turned out that the implementation converges nicely for any value of interest; nevertheless, the curiosity remains...) > > I can see few line of actions that would make sense > > [1] Raise an exception. > > Maybe this is a bit too drastic since there are cases where a moderate loss of precision does not matter (this was my case, i just needed one or two decimal digits) > > [2] Let the function have an optional "precision" parameter and raise an exception if the precision goes below that > > [3] Let the function return a record with a field Value with the actual result and a field Error with the estimated precision. > > This would make the code a bit heavier since instead of calling > > X := Lambert(Y); > > you would say > > X := Lambert(Y).Value; > > Not really a huge deal, however... > > [4] Print a warning message to standard error or some logging system and go on. > > This sounds like the worst option to me. The message could be overlooked and, moreover, it supposes there is some logging facilities or that the standard error is available for logging... Remember that the function should be general, to be used in any program. > > [5] ??? > > Any suggestions? > > Thank you in advance > > Riccardo > Most Fortran Lapack use INFO code. " All documented routines have a diagnostic argument INFO that indicates the success or failure of the computation, as follows: INFO = 0: successful termination INFO < 0: illegal value of one or more arguments -- no computation performed INFO > 0: failure in the course of computation " https://www.netlib.org/lapack/lug/node138.html So you could follow that. Another option is to throw an exception. So your program will look like try X= Lambert(Y,....); ... if you get here, then no error catch: ..... error happend. handle it end try --Nasser