UNPKG

kld-polynomial

Version:

A class of simple polynomial functionality including root finding

3 lines (2 loc) 11.9 kB
!function(e,t){"object"==typeof exports&&"undefined"!=typeof module?t(exports):"function"==typeof define&&define.amd?define(["exports"],t):t((e=e||self).KldPolynomial={})}(this,function(e){"use strict";function t(e,t){if(!(e instanceof t))throw new TypeError("Cannot call a class as a function")}function r(e,t){for(var r=0;r<t.length;r++){var a=t[r];a.enumerable=a.enumerable||!1,a.configurable=!0,"value"in a&&(a.writable=!0),Object.defineProperty(e,a.key,a)}}function a(e,t,a){return t&&r(e.prototype,t),a&&r(e,a),e}function n(e){return(n=Object.setPrototypeOf?Object.getPrototypeOf:function(e){return e.__proto__||Object.getPrototypeOf(e)})(e)}function o(e,t){return(o=Object.setPrototypeOf||function(e,t){return e.__proto__=t,e})(e,t)}function s(e,t){return!t||"object"!=typeof t&&"function"!=typeof t?function(e){if(void 0===e)throw new ReferenceError("this hasn't been initialised - super() hasn't been called");return e}(e):t}function i(e,t,r){return(i="undefined"!=typeof Reflect&&Reflect.get?Reflect.get:function(e,t,r){var a=function(e,t){for(;!Object.prototype.hasOwnProperty.call(e,t)&&null!==(e=n(e)););return e}(e,t);if(a){var o=Object.getOwnPropertyDescriptor(a,t);return o.get?o.get.call(r):o.value}})(e,t,r||e)}function u(e){return"number"==typeof e?e?e<0?-1:1:e==e?e:NaN:NaN}var h=function(){function e(){t(this,e),this.coefs=[];for(var r=arguments.length-1;r>=0;r--)this.coefs.push(r<0||arguments.length<=r?void 0:arguments[r]);this._variable="t",this._s=0}return a(e,[{key:"clone",value:function(){var t=new e;return t.coefs=this.coefs.slice(),t}},{key:"eval",value:function(e){if(isNaN(e))throw new TypeError("Parameter must be a number. Found '".concat(e,"'"));for(var t=0,r=this.coefs.length-1;r>=0;r--)t=t*e+this.coefs[r];return t}},{key:"add",value:function(t){for(var r=new e,a=this.getDegree(),n=t.getDegree(),o=Math.max(a,n),s=0;s<=o;s++){var i=s<=a?this.coefs[s]:0,u=s<=n?t.coefs[s]:0;r.coefs[s]=i+u}return r}},{key:"multiply",value:function(t){for(var r=new e,a=0;a<=this.getDegree()+t.getDegree();a++)r.coefs.push(0);for(var n=0;n<=this.getDegree();n++)for(var o=0;o<=t.getDegree();o++)r.coefs[n+o]+=this.coefs[n]*t.coefs[o];return r}},{key:"divideEqualsScalar",value:function(e){for(var t=0;t<this.coefs.length;t++)this.coefs[t]/=e}},{key:"simplifyEquals",value:function(){for(var e=arguments.length>0&&void 0!==arguments[0]?arguments[0]:1e-12,t=this.getDegree();t>=0&&Math.abs(this.coefs[t])<=e;t--)this.coefs.pop()}},{key:"removeZerosEquals",value:function(){for(var e=arguments.length>0&&void 0!==arguments[0]?arguments[0]:1e-15,t=this.coefs,r=10*e*Math.abs(t.reduce(function(e,t){return Math.abs(t)>Math.abs(e)?t:e})),a=0;a<t.length-1;a++)Math.abs(t[a])<r&&(t[a]=0);return this}},{key:"monicEquals",value:function(){var e=this.coefs;return 1!==e[e.length-1]&&this.divideEqualsScalar(e[e.length-1]),this}},{key:"toString",value:function(){for(var e=[],t=[],r=this.coefs.length-1;r>=0;r--){var a=Math.round(1e3*this.coefs[r])/1e3;if(0!==a){var n=a<0?" - ":" + ";a=Math.abs(a),r>0&&(1===a?a=this._variable:a+=this._variable),r>1&&(a+="^"+r),t.push(n),e.push(a)}}t[0]=" + "===t[0]?"":"-";for(var o="",s=0;s<e.length;s++)o+=t[s]+e[s];return o}},{key:"bisection",value:function(e,t){var r,a=arguments.length>2&&void 0!==arguments[2]?arguments[2]:1e-6,n=arguments.length>3&&void 0!==arguments[3]?arguments[3]:15,o=this.eval(e),s=this.eval(t);if(Math.abs(o)<=a)r=e;else if(Math.abs(s)<=a)r=t;else if(o*s<=0)for(var i=Math.log(t-e),u=Math.LN10*n,h=Math.ceil((i+u)/Math.LN2),f=0;f<h;f++){r=.5*(e+t);var c=this.eval(r);if(Math.abs(c)<=a)break;c*o<0?(t=r,s=c):(e=r,o=c)}return r}},{key:"trapezoid",value:function(e,t,r){if(isNaN(e)||isNaN(t)||isNaN(r))throw new TypeError("Parameters must be numbers");var a=t-e;if(1===r){var n=this.eval(e),o=this.eval(t);this._s=.5*a*(n+o)}else{for(var s=1<<r-2,i=a/s,u=e+.5*i,h=0,f=0;f<s;f++)h+=this.eval(u),u+=i;this._s=.5*(this._s+a*h/s)}if(isNaN(this._s))throw new TypeError("this._s is NaN");return this._s}},{key:"simpson",value:function(e,t){if(isNaN(e)||isNaN(t))throw new TypeError("Parameters must be numbers");for(var r=t-e,a=.5*r*(this.eval(e)+this.eval(t)),n=a,o=4*a/3,s=o,i=a,u=1,h=2;h<=20;h++){for(var f=r/u,c=e+.5*f,l=0,v=1;v<=u;v++)l+=this.eval(c),c+=f;if(o=(4*(a=n=.5*(n+r*l/u))-i)/3,Math.abs(o-s)<1e-7*Math.abs(s))break;s=o,i=a,u<<=1}return o}},{key:"romberg",value:function(t,r){if(isNaN(t)||isNaN(r))throw new TypeError("Parameters must be numbers");var a=new Array(21),n=new Array(21),o={y:0,dy:0};n[0]=1;for(var s=1;s<=20&&(a[s-1]=this.trapezoid(t,r,s),!(s>=3&&(o=e.interpolate(n,a,3,s-3,0),Math.abs(o.dy)<=1e-6*o.y)));s++)a[s]=a[s-1],n[s]=.25*n[s-1];return o.y}},{key:"zeroErrorEstimate",value:function(e){if(void 0===e){var t=this.bounds();e=Math.max(Math.abs(t.minX),Math.abs(t.maxX))}if(e<.001)return 2*Math.abs(this.eval(1e-15));var r=this.coefs.length-1,a=this.coefs[r];return 10*1e-15*this.coefs.reduce(function(t,r,n){var o=r/a*Math.pow(e,n);return o>t?o:t},0)}},{key:"boundsUpperRealFujiwara",value:function(){var e=this.coefs,t=e.length-1,r=e[t];1!==r&&(e=this.coefs.map(function(e){return e/r}));var a,n=e.map(function(e,r){return r<t?Math.pow(Math.abs(0===r?e/2:e),1/(t-r)):e}),o=function(e,t,r){return a(r)&&(e.max<t?(e.nearmax=e.max,e.max=t):e.nearmax<t&&(e.nearmax=t)),e};a=function(r){return r<t&&e[r]<0};var s=n.reduce(o,{max:0,nearmax:0});return a=function(r){return r<t&&(t%2==r%2?e[r]<0:e[r]>0)},{negX:-2*n.reduce(o,{max:0,nearmax:0}).max,posX:2*s.max}}},{key:"boundsLowerRealFujiwara",value:function(){var t=new e;t.coefs=this.coefs.slice().reverse();var r=t.boundsUpperRealFujiwara();return r.negX=1/r.negX,r.posX=1/r.posX,r}},{key:"bounds",value:function(){var e=this.boundsUpperRealFujiwara(),t={minX:e.negX,maxX:e.posX};return 0===e.negX&&0===e.posX?t:(0===e.negX?t.minX=this.boundsLowerRealFujiwara().posX:0===e.posX&&(t.maxX=this.boundsLowerRealFujiwara().negX),t.minX>t.maxX&&(t.minX=t.maxX=0),t)}},{key:"boundUpperAbsRouche",value:function(){var e=this.coefs,t=e.length-1;return 1+e.reduce(function(e,r,a){return a!==t&&e<(r=Math.abs(r))?r:e},0)/Math.abs(e[t])}},{key:"boundLowerAbsRouche",value:function(){var e=this.coefs,t=e.reduce(function(e,t,r){return 0!==r&&e<(t=Math.abs(t))?t:e},0);return Math.abs(e[0])/(Math.abs(e[0])+t)}},{key:"boundsRealLaguerre",value:function(){var e=this.coefs,t=e.length-1,r=-e[t-1]/(t*e[t]),a=e[t-1]*e[t-1]-2*t/(t-1)*e[t]*e[t-2],n=(t-1)/(t*e[t])*Math.sqrt(a);return n<0&&(n=-n),{minX:r-n,maxX:r+n}}},{key:"countRootsDescartes",value:function(){var e=this.coefs,t=e.length-1,r=e.reduce(function(e,t,r){return 0!==e.prev_a&&0!==t&&(e.prev_a<0==t>0&&e.pos++,r%2==0!=e.prev_a<0==(r%2==1!=t>0)&&e.neg++),e.prev_a=t,e},{pos:0,neg:0,prev_a:0});return{maxRealPos:r.pos,maxRealNeg:r.neg,minComplex:t-(r.pos+r.neg)}}},{key:"getDegree",value:function(){return this.coefs.length-1}},{key:"getDerivative",value:function(){for(var t=new e,r=1;r<this.coefs.length;r++)t.coefs.push(r*this.coefs[r]);return t}},{key:"getRoots",value:function(){var e;switch(this.simplifyEquals(),this.getDegree()){case 0:e=[];break;case 1:e=this.getLinearRoot();break;case 2:e=this.getQuadraticRoots();break;case 3:e=this.getCubicRoots();break;case 4:e=this.getQuarticRoots();break;default:e=[]}return e}},{key:"getRootsInInterval",value:function(e,t){var r=[];function a(e){"number"==typeof e&&r.push(e)}if(0===this.getDegree())throw new RangeError("Unexpected empty polynomial");if(1===this.getDegree())a(this.bisection(e,t));else{var n=this.getDerivative().getRootsInInterval(e,t);if(n.length>0){a(this.bisection(e,n[0]));for(var o=0;o<=n.length-2;o++)a(this.bisection(n[o],n[o+1]));a(this.bisection(n[n.length-1],t))}else a(this.bisection(e,t))}return r}},{key:"getLinearRoot",value:function(){var e=[],t=this.coefs[1];return 0!==t&&e.push(-this.coefs[0]/t),e}},{key:"getQuadraticRoots",value:function(){var e=[];if(2===this.getDegree()){var t=this.coefs[2],r=this.coefs[1]/t,a=r*r-4*(this.coefs[0]/t);if(a>0){var n=Math.sqrt(a);e.push(.5*(-r+n)),e.push(.5*(-r-n))}else 0===a&&e.push(.5*-r)}return e}},{key:"getCubicRoots",value:function(){var e=[];if(3===this.getDegree()){var t=this.coefs[3],r=this.coefs[2]/t,a=this.coefs[1]/t,n=(3*a-r*r)/3,o=(2*r*r*r-9*a*r+27*(this.coefs[0]/t))/27,s=r/3,i=o*o/4+n*n*n/27,u=o/2,h=this.zeroErrorEstimate();if(Math.abs(i)<=h&&(i=0),i>0){var f,c=Math.sqrt(i),l=-u+c;f=l>=0?Math.pow(l,1/3):-Math.pow(-l,1/3),(l=-u-c)>=0?f+=Math.pow(l,1/3):f-=Math.pow(-l,1/3),e.push(f-s)}else if(i<0){var v=Math.sqrt(-n/3),p=Math.atan2(Math.sqrt(-i),-u)/3,b=Math.cos(p),g=Math.sin(p),y=Math.sqrt(3);e.push(2*v*b-s),e.push(-v*(b+y*g)-s),e.push(-v*(b-y*g)-s)}else{var m;m=u>=0?-Math.pow(u,1/3):Math.pow(-u,1/3),e.push(2*m-s),e.push(-m-s)}}return e}},{key:"getQuarticRoots",value:function(){var t=[],r=this.getDegree();if(4===r){var a=new e;a.coefs=this.coefs.slice(),a.divideEqualsScalar(a.coefs[r]);Math.abs(a.coefs[0])<10*1e-15*Math.abs(a.coefs[3])&&(a.coefs[0]=0);for(var n=a.getDerivative(),o=n.getRoots().sort(function(e,t){return e-t}),s=[],i=o.length-1,h=this.bounds(),f=Math.max(Math.abs(h.minX),Math.abs(h.maxX)),c=this.zeroErrorEstimate(f),l=0;l<=i;l++)s.push(a.eval(o[l]));for(var v=0;v<=i;v++)Math.abs(s[v])<c&&(s[v]=0);var p=0,b=Math.max(.1*(h.maxX-h.minX)/r,1e-15),g=[],y=[];if(i>-1){for(0!==s[0]?u(s[0])!==u(a.eval(o[0]-b)-s[0])&&(g.push(o[0]-b),y.push([h.minX,o[0]])):(t.push(o[0],o[0]),p++);p<i;p++)0===s[p+1]?(t.push(o[p+1],o[p+1]),p++):u(s[p])!==u(s[p+1])&&(g.push((o[p]+o[p+1])/2),y.push([o[p],o[p+1]]));0!==s[i]&&u(s[i])!==u(a.eval(o[i]+b)-s[i])&&(g.push(o[i]+b),y.push([o[i],h.maxX]))}var m=function(e){return a.eval(e)},w=function(e){return n.eval(e)};if(g.length>0)for(p=0;p<g.length;p++)g[p]=e.newtonSecantBisection(g[p],m,w,32,y[p][0],y[p][1]);t=t.concat(g)}return t}}],[{key:"interpolate",value:function(e,t,r,a,n){if(e.constructor!==Array||t.constructor!==Array)throw new TypeError("xs and ys must be arrays");if(isNaN(r)||isNaN(a)||isNaN(n))throw new TypeError("n, offset, and x must be numbers");var o,s,i=0,u=new Array(r),h=new Array(r),f=0,c=Math.abs(n-e[a]);for(o=0;o<r;o++){var l=Math.abs(n-e[a+o]);l<c&&(f=o,c=l),u[o]=h[o]=t[a+o]}s=t[a+f],f--;for(var v=1;v<r;v++){for(o=0;o<r-v;o++){var p=e[a+o]-n,b=e[a+o+v]-n,g=u[o+1]-h[o],y=p-b;if(0===y)throw new RangeError("Unable to interpolate polynomial. Two numbers in n were identical (to within roundoff)");y=g/y,h[o]=b*y,u[o]=p*y}s+=i=2*(f+1)<r-v?u[f+1]:h[f--]}return{y:s,dy:i}}},{key:"newtonSecantBisection",value:function(e,t,r,a,n,o){var s,i,h,f,c,l,v,p=0,b=0;s=e;var g=Math.pow(10,-14),y="number"==typeof n&&"number"==typeof o;if(y){if(n>o)throw new RangeError("Min must be greater than max");if(l=t(n),v=t(o),u(l)===u(v))throw new RangeError("Y values of bounds must be of opposite sign")}for(var m=function(){return Math.abs(h)<=g*Math.abs(s)||b===s-h-s},w=0;w<a;w++){if(0===(i=r(s))){if(0===p)throw new RangeError("df(x) is zero");i=p}if(p=i,c=t(s),f=s-(h=c/i),m())break;if(y){if(u(c)===u(v))o=s,v=c;else{if(u(c)!==u(l)){s=f;break}n=s,l=c}if(f<n||f>o){if(u(l)===u(v))break;var d=v-l,M=o-n;if(h=0===d?s-(n+.5*M):Math.abs(d/Math.min(l,v))>50?s-(n+M*(.5+(Math.abs(l)<Math.abs(v)?-.25:.25))):s-(n-l/d*M),f=s-h,m())break}}b=s-f,s=f}return s}}]),e}(),f=function(e){function r(){return t(this,r),s(this,n(r).apply(this,arguments))}return function(e,t){if("function"!=typeof t&&null!==t)throw new TypeError("Super expression must either be null or a function");e.prototype=Object.create(t&&t.prototype,{constructor:{value:e,writable:!0,configurable:!0}}),t&&o(e,t)}(r,h),a(r,[{key:"eval",value:function(e){var t=i(n(r.prototype),"eval",this).call(this,e);if(Math.abs(t)<1e-7&&(t=0),t<0)throw new RangeError("Cannot take square root of negative number");return Math.sqrt(t)}},{key:"toString",value:function(){return"sqrt("+i(n(r.prototype),"toString",this).call(this)+")"}}]),r}();e.Polynomial=h,e.SqrtPolynomial=f,Object.defineProperty(e,"__esModule",{value:!0})}); //# sourceMappingURL=index-umd.min.js.map