matlab - How to avoid loss of accuracy when converting symbolic expressions to functions? -


tl;dr: observe complete loss of accuracy when converting symbolic expression function handle matlabfunction. wonder if there ways improve conversion in order avoid loss of accuracy.


i have symbolic variable x 1 <= x && x <= 2 holds true:

syms x real assumealso(1 <= x & x <= 2); 

i have many computer-generated, lengthy symbolic expression in variable. 1 of them looks this:

expression = ( ...   1015424780204960143215273323910078528628754663952913658657288835138029704791686717561885487746105223164496264397062144000 ...   *( ...      60345244216851610523130575942127473698515638085026410114070496399315754724985170479034760688327679099512793302302720*2^(1/2) ...    - 85341062796188128379389251264141456937242003828816791711306294886439805159655912635773490018204138847163921224639041 ...    )*(x - 2)^2 ... ) ... /31504288346872372712061562812941419427167561153216213605146864117586323331155800294021400857537041202039565879856190821729945216935526707438840242294801134287960934949194864204307116208568439380511702602881; 

edit: have construct (pasting above make expression constant 0)

expression = sym('(1015424780204960143215273323910078528628754663952913658657288835138029704791686717561885487746105223164496264397062144000*(60345244216851610523130575942127473698515638085026410114070496399315754724985170479034760688327679099512793302302720*2^(1/2) - 85341062796188128379389251264141456937242003828816791711306294886439805159655912635773490018204138847163921224639041)*(x - 2)^2)/31504288346872372712061562812941419427167561153216213605146864117586323331155800294021400857537041202039565879856190821729945216935526707438840242294801134287960934949194864204307116208568439380511702602881'); 

calling double(subs(expression, x, 1)) evaluates expression approximately -5.9492e+03 without problems, correct value. however, evaluation takes far long , huge (or rather tiny?) bottleneck in application. that’s why intend convert expression anonymous function operates on doubles , faster, so:

evaluator = matlabfunction(expression, 'vars', x); 

the result being

@(x) (sqrt(2.0).*6.034524421685161e115-8.534106279618813e115) ... .*(x-2.0).^2.*3.223131940086397e-86 

i had success approach in past. unfortunately in case, evaluator(x) evaluates 0 value of x, because first row zero. obviously, has limited number of significant digits doubles.

are there ways work around this? can tell matlab consider range of x can find better representation of constants?

the problem can fixed variable-precision arithmetic:

>> expr = vpa(expression) expr = -5949.2156936801140978790460880789*(x - 2.0)^2 

convert function

>> func =   function_handle value:     @(x)(x-2.0).^2.*-5.949215693680114e3 

then evaluate it

>> func(1) ans =   -5.9492e+03 

Comments

Popular posts from this blog

javascript - Clear button on addentry page doesn't work -

c# - Selenium Authentication Popup preventing driver close or quit -

tensorflow when input_data MNIST_data , zlib.error: Error -3 while decompressing: invalid block type -