1 2 /** 3 * @name CeL function for math 4 * @fileoverview 5 * 本檔案包含了數學演算相關的 functions。 6 * @since 7 */ 8 9 /* 10 TODO: 11 大數計算 12 方程式圖形顯示 by SVG 13 */ 14 15 16 17 if (typeof CeL === 'function') 18 CeL.setup_module('data.math', 19 { 20 require : 'data.split_String_to_Object', 21 code : function(library_namespace, load_arguments) { 22 23 // requiring 24 var split_String_to_Object; 25 eval(library_namespace.use_function(this)); 26 27 28 29 /** 30 * null module constructor 31 * @class 數學相關的 functions 32 */ 33 CeL.data.math 34 = function() { 35 // null module constructor 36 }; 37 38 /** 39 * for JSDT: 有 prototype 才會將之當作 Class 40 */ 41 CeL.data.math 42 .prototype = { 43 }; 44 45 46 47 48 49 /* 50 Math --------------------------------------------------------------- 51 */ 52 53 /* 54 //{var v=Math.LN2,d=mutual_division(v),q=to_rational_number(v);alert('值 '+v+'\n序列 '+d+'\n近似值 '+q[0]+' / '+q[1]+'\n約 '+(q=q[0]/q[1])+'\n值-近似 '+(q-=v)+'\n差'+(Math.abs(q=10000*q/v)>1?'萬分之'+q.to_fixed(2)+' ( '+q+' / 10000 )':'億分之'+(q*=10000).to_fixed(2)+' ( '+q+' / 100000000 )'),0,'近似值 '+v);} 55 56 //{var d=new Date,a=.142857,b=1000000,i=0,c;for(i=0;i<10000;i++)c=mutual_division(a);alert(c+'\n'+gDate(new Date-d));} 57 */ 58 59 CeL.data.math 60 . 61 /** 62 * 輾轉相除 n1/n2 或 小數 n1/1 轉成 整數/整數 63 * @param {Number} n1 number 1 64 * @param {Number} [n2] number 2 65 * @param {Number} times max 次數, 1,2,.. 66 * @return {Array} 連分數序列 ** 負數視 _.mutual_division.done 而定! 67 */ 68 mutual_division = function mutual_division(n1, n2, times) { 69 var q = [], c; 70 if (isNaN(times) || times <= 0) 71 times = 80; 72 if (!n2 || isNaN(n2)) 73 n2 = 1; 74 75 if (n1 != Math.floor(n1)) { 76 c = n1; 77 var i = 9, f = n2; 78 while (i--) 79 // 以整數運算比較快!這樣會造成整數多4%,浮點數多1/3倍的時間,但仍值得。 80 if (f *= 10, c *= 10, c === Math.floor(c)) { 81 n1 = c, n2 = f; 82 break; 83 } 84 } 85 86 // 連分數負數之處理。更沒問題的: (n1 < 0?1:0) ^ (n2 < 0?1:0) 87 if (_.mutual_division.mode && ((n1 < 0) ^ (n2 < 0))) { 88 // 使兩數皆為正 89 if (n2 < 0) 90 n2 = -n2; 91 else 92 n1 = -n1; 93 94 q.push(-(1 + (n1 - (c = n1 % n2)) / n2)); 95 n1 = n2, n2 -= c; 96 } 97 98 /* old: 99 while(b&&n--) 100 d.push((a-(c=a%b))/b),a=b,b=c; // 2.08s@10000 可能因為少設定(=)一次c所以較快。但(若輸入不為整數)不確保d為整數?用Math.floor((a-(c=a%b))/b)可確保,速度與下式一樣快。 101 //d.push(c=Math.floor(a/b)),c=a-b*c,a=b,b=c; // 2.14s@10000:mutual_division(.142857) 102 //d.push(Math.floor(a/b)),b=a%(c=b),a=c; // 2.2s@10000 103 //if(n)d.push(0); 104 */ 105 106 // 2.4s@10000 可能因為少設定(=)一次c所以較快。但(若輸入不為整數)不確保d為整數?用Math.floor((a-(c=a%b))/b)可確保,速度與下式一樣快。 107 while (times--) 108 if (n2) 109 q.push((n1 - (c = n1 % n2)) / n2), n1 = n2, n2 = c; 110 else { 111 // [ .. , done mark, (最後非零的餘數。若原 n1, n2 皆為整數,則此值為 GCD。但請注意:這邊是已經經過前面為了以整數運算,增加倍率過的數值!!) ] 112 q.push(_.mutual_division.done, n1); 113 //library_namespace.debug('done: ' + q); 114 break; 115 } 116 117 // 2.26s@10000 118 //while(b&&n--)if(d.push((a-(c=a%b))/b),a=b,!(b=c)){d.push(0);break;} 119 120 //var m=1;c=1;while(m&&n--)d.push(m=++c%2?b?(a-(a%=b))/b:0:a?(b-(b%=a))/a:0);//bug 121 122 return q; 123 }; 124 CeL.data.math 125 . 126 mutual_division.done = -7;//'' 127 128 CeL.data.math 129 . 130 /** 131 * !!mode:連分數處理,對負數僅有最初一數為負。 132 */ 133 mutual_division.mode = 0; 134 135 CeL.data.math 136 . 137 /** 138 * 取得連分數序列的數值 139 * @param {Array} sequence 序列 140 * @param {Number} [max_no] 取至第 max_no 個 141 * @requires mutual_division.done 142 * @return 143 * @see 144 * var a=continued_fraction([1,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2]); 145 * alert(a+'\n'+a[0]/a[1]+'\n'+Math.SQRT2+'\n'+(Math.SQRT2-a[0]/a[1])+'\n'+mutual_division(a[0],a[1])); 146 */ 147 continued_fraction = function(sequence, max_no) { 148 if (!library_namespace.is_Array(sequence) || !sequence.length) 149 return sequence; 150 151 if (sequence[sequence.length - 2] === _.mutual_division.done) 152 sequence.length -= 2; 153 154 if (sequence.length < 1) 155 return sequence; 156 157 if (!max_no/* ||max_no<2 */|| max_no > sequence.length) 158 max_no = sequence.length; 159 160 var a, b; 161 if (max_no % 2) 162 b = 1, a = 0; 163 else 164 a = 1, b = 0; 165 //sequence[max_no++]=1;if(--max_no%2)b=sequence[max_no],a=s[--max_no];else a=sequence[max_no],b=sequence[--max_no]; 166 167 //library_namespace.debug('a=' + a + ', b=' + b + ', max_no=' + max_no); 168 while (max_no--) 169 if (max_no % 2) 170 b += a * sequence[max_no]; 171 else 172 a += b * sequence[max_no]; 173 //library_namespace.debug('a=' + a + ', b=' + b); 174 return [ a, b ]; 175 }; 176 177 178 CeL.data.math 179 . 180 /** 181 * The best rational approximation. 取得值最接近之有理數 (use 連分數 continued fraction), 取近似值. 182 * c.f., 調日法 183 * 在分子或分母小於下一個漸進分數的分數中,其值是最接近精確值的近似值。 184 * @example 185 * to_rational_number(4088/783) 186 * @param {Number} number number 187 * @param {Number} [rate] 比例在 rate 以上 188 * @param {Number} [max_no] 最多取至序列第 max_no 個 189 * TODO : 並小於 l: limit 190 * @return [分子, 分母, 誤差] 191 * @requires mutual_division,continued_fraction 192 * @see 193 * http://en.wikipedia.org/wiki/Continued_fraction#Best_to_rational_numbers 194 */ 195 to_rational_number = function(number, rate, max_no) { 196 if (!rate) 197 // This is a magic number: 我們無法準確得知其界限為何。 198 rate = 65536; 199 var d = _.mutual_division(number, 1, max_no && max_no > 0 ? max_no : 20), 200 i = 0, a, b = d[0], done = _.mutual_division.done; 201 202 if (!b) 203 b = d[++i]; 204 while (++i < d.length && (a = d[i]) !== done) 205 if (a / b < rate) 206 b = a; 207 else 208 break; 209 210 if(0) 211 library_namespace.debug( 212 number + ' ' + 213 // 連分數表示 214 (d.length > 1 && d[d.length - 2] === _.mutual_division.done ? 215 '=' + ' [<em>' + d[0] + ';' + d.slice(1, i).join(', ') + '</em>' 216 + (i < d.length - 2 ? ', ' + d.slice(i, -2).join(', ') : '') 217 + '] .. ' + d.slice(-1) : 218 // 約等於的符號是≈或≒,不等於的符號是≠。 219 // http://zh.wikipedia.org/wiki/%E7%AD%89%E4%BA%8E 220 '≈' + ' [<em>' + d[0] + ';' + d.slice(1, i).join(', ') + '</em>' 221 + (i < d.length ? ', ' + d.slice(i).join(', ') : '') + ']: ' 222 + d.length + ',' + i + ',' + d[i] 223 ) 224 ); 225 d = _.continued_fraction(d, i); 226 //library_namespace.debug('→ ' + d[0] + '/' + d[1]); 227 if (d[1] < 0) 228 d[0] = -d[0], d[1] = -d[1]; 229 230 return [ d[0], d[1], d[0] / d[1] - number ]; 231 }; 232 233 234 /* 最大公因數/公約數 Greatest Common Divisor 235 236 usage: 237 gcd(6,9) 238 GCD([5,3,8,2,6,9]) 239 */ 240 //_gcd[generateCode.dLK]='mutual_division,mutual_division_done'; 241 function _gcd(a,b){ 242 if(isNaN(a)||isNaN(b)) 243 return isNaN(b)?a:b; 244 245 var d=_.mutual_division(a,b); 246 a=d.pop(); 247 if(d.pop()===_.mutual_division.done) 248 return a; 249 } 250 251 CeL.data.math 252 . 253 /** 254 * Get GCD of 2 numbers 255 * @param n1 number 1 256 * @param n2 number 2 257 * @return GCD of the 2 numbers 258 */ 259 gcd = function(n1, n2) { 260 /* 261 if (isNaN(a)) 262 return b; 263 */ 264 // 必要! 265 if (!n2 || isNaN(n2)) 266 return n1; 267 268 // 也可最後再 Math.abs 269 /* 270 if (a < 0) 271 a = -a; 272 if (b < 0) 273 b = -b; 274 */ 275 276 // Euclidean algorithm 277 var r; 278 while (r = n1 % n2) 279 n1 = n2, n2 = r; 280 return n2 < 0 ? -n2 : n2; 281 }; 282 283 //GCD[generateCode.dLK]='gcd'; 284 function GCD(numA){ 285 var i=1,g=numA[0]; 286 for(;i<numA.length;i++) 287 if(!isNaN(numA[i])) 288 g=gcd(g,numA[i]); 289 return g; 290 } 291 /* 最小公倍數 Least Common Multiple 292 293 usage: 294 lcm(6,9) 295 lcm([5,3,8,2,6,9]) 296 297 TODO: 298 更快的方法: 299 短除法 300 一次算出 GCD, LCM 301 */ 302 //lcm[generateCode.dLK]='gcd'; 303 function lcm(a,b){ 304 var l,g,i=1; 305 if( typeof a=='object' && !isNaN(l=a[0]) ){ 306 while(i<a.length) 307 l=lcm(l,a[i++]); 308 return l; 309 } 310 311 if( (g=gcd(a,b)) && !isNaN(g) ) 312 return a/g*b; 313 } 314 315 316 /* 317 http://www.math.umbc.edu/~campbell/NumbThy/Class/Programming/JavaScript.html 318 http://aoki2.si.gunma-u.ac.jp/JavaScript/ 319 */ 320 321 CeL.data.math 322 . 323 /** 324 * 得到平方數,相當於 Math.floor(Math.sqrt(number)). 325 * get integer square root 326 * @param {Number} positive number 327 * @return r, r^2 <= number < (r+1)^2 328 * @example 329 * var p = 20374345, q = CeL.math.floor_sqrt(p = p * p - 1); CeL.log(q + '<br/>' + (q * q) + '<br/>' + p + '<br/>' + (++q * q)); 330 * @see 331 * <a href="http://www.azillionmonkeys.com/qed/sqroot.html" accessdate="2010/3/11 18:37">Paul Hsieh's Square Root page</a> 332 * <a href="http://www.embeddedrelated.com/usenet/embedded/show/114789-1.php" accessdate="2010/3/11 18:34">Suitable Integer Square Root Algorithm for 32-64-Bit Integers on Inexpensive Microcontroller? | Comp.Arch.Embedded | EmbeddedRelated.com</a> 333 */ 334 floor_sqrt = function(number){ 335 if (isNaN(number = Math.floor(number))) 336 return; 337 var g = 0, v, h, t; 338 while ((t = g << 1) < (v = number - g * g)) { 339 //library_namespace.debug(t + ', ' + v); 340 h = 1; 341 while (h * (h + t) <= v) 342 // 因為型別轉關係,還是保留 << 而不用 *2 343 h <<= 1;//h *= 2; 344 g += h >> 1;//h / 2;// 345 } 346 //library_namespace.debug('end: ' + t + ', ' + v); 347 return g; 348 }; 349 350 351 CeL.data.math 352 . 353 /** 354 * 取得某數的質因數,因式分解/素因子分解, factorization, get floor factor. 355 * 唯一分解定理(The Unique Factorization Theorem)告訴我們素因子分解是唯一的,這即是稱為算術基本定理 (The Fundamental Theorem of Arithmeric) 的數學金科玉律。 356 * @param {Number} number 357 * @return {Array} [prime1,power1,prime2,power2,..] 358 * @see 359 * <a href="http://homepage2.nifty.com/m_kamada/math/10001.htm" accessdate="2010/3/11 18:7">Factorizations of 100...001</a> 360 * @requires floor_sqrt 361 */ 362 factorization = function(number) { 363 var f = 2, p, a, l, r = []; 364 if (isNaN(number) || number < 1 || number > 365 /* 366 * javascript 可以表示的最大整數值 367 * 10^21-2^16-1 = 999999999999999934463 368 * @see 369 * http://www.highdots.com/forums/javascript/how-js-numbers-represented-internally-166538-4.html 370 */ 371 999999999999999934469) 372 return; 373 number = Math.floor(number); 374 375 // 2,3 376 while (number > 1) { 377 if (number % f === 0) { 378 p = 0; 379 do 380 number /= f, p++; 381 while (number % f === 0); // do{n/=f,p++;}while(n%f==0); 382 r.push(f, p); 383 } 384 if (++f > 3) 385 break; 386 } 387 388 a = 4, f = 5, l = _.floor_sqrt(number); // 5-初始化 389 while (number > 1) { 390 if (f > l) { 391 r.push(number, 1); 392 break; 393 } 394 // document.write('<br/>'+f+','+n); 395 if (number % f === 0) { 396 p = 0; 397 do { 398 number /= f, p++; 399 } while (number % f === 0); 400 l = _.floor_sqrt(number), r.push(f, p); 401 } 402 f += a = a === 2 ? 4 : 2; 403 } 404 return r; 405 }; 406 407 /* test 408 function count(n){ 409 var a=factorization(n),s='',v=1; 410 if(a){ 411 for(var i=0;i<a.length;i+=2){s+='*'+a[i]+(a[i+1]>1?'^'+a[i+1]:'');v*=Math.pow(a[i],a[i+1]);} 412 s=s.substr(1)+'='+v+'='+n; 413 }else s='error! '+n; 414 document.getElementById('result').value+=s+'\n-------------------------------------------\n'; 415 } 416 */ 417 418 419 /* 猜測一個數可能的次方數。 2005/2/18 19:20未完成 420 type=0:整數,1:有理數 421 return [base分子,base分母,exponent分子,exponent分母] 422 */ 423 function to_exponent(num,type){ 424 var bn,bd,en=1,ed,sq=[1,num],t,q,error=1e-9,g=function(n){q=_.to_rational_number(n,99999);if((!type||q[1]==1)&&!(q[0]>99999&&q[1]>99999)&&q[2]/n<error)bn=q[0],bd=q[1],ed=t;};//error:誤差 425 426 if(!ed)g(sq[t=1]); 427 if(!ed)g(sq[t=2]=sq[1]*sq[1]); 428 if(!ed)g(sq[t=3]=sq[1]*sq[2]); 429 if(!ed)g(sq[t=4]=sq[2]*sq[2]); 430 if(!ed)g(sq[t=5]=sq[2]*sq[3]); 431 if(!ed)bn=num,bd=ed=1; 432 433 return [bn,bd,en,ed]; 434 } 435 //var t=to_exponent(Math.pow(2/3,1/1));alert(t[0]+'/'+t[1]+'^'+t[2]+'/'+t[3]); 436 437 438 439 440 /* 441 for 出題 442 443 runCode.setR=0; 444 for(var i=0,j,t,s,n_e;i<10;){ 445 t=2000+8000*Math.random(); 446 s=get_random_prime.get_different_number_set(3,t,t/8); 447 if(s.LCM>9999)continue; 448 n_e=[]; 449 n_e[s.GCD]=1; 450 for(j=0;j<s.length;j++) 451 if(n_e[s[j]])continue; 452 else n_e[s[j]]=1; 453 sl([s.GCD,s.LCM]+'<b style="color:#c4a">;</b> '+s);i++; 454 } 455 456 */ 457 458 // 求乘積 459 function get_product(nums,till){ // num array, 乘到比till小就回傳 460 var p=1,i=0,l=nums.length; 461 for(;i<l;i++){ 462 if(till&&p*nums[i]>till)break; 463 p*=nums[i]; 464 } 465 return p; 466 } 467 468 469 // 2009/10/21 11:57:47 470 //get_random_prime[generateCode.dLK]='get_product'; 471 get_random_prime.primes=[2,3,5,7,11,13,17,19,23,29,31,37,41,43,47,53,59,61,67,71,73,79,83,89,97,101,103,107,109,113,127,131,137,139,149,151,157,163,167,173,179,181,191,193,197,199,211,223,227,229,233,239,241,251,257,263,269,271,277,281,283,293,307,311,313,317,331,337,347,349,353,359,367,373,379,383,389,397,401,409,419,421,431,433,439,443,449,457,461,463,467,479,487,491,499,503,509,521,523,541,547,557,563,569,571,577,587,593,599,601,607,613,617,619,631,641,643,647,653,659,661,673,677,683,691,701,709,719,727,733,739,743,751,757,761,769,773,787,797,809,811,821,823,827,829,839,853,857,859,863,877,881,883,887,907,911,919,929,937,941,947,953,967,971,977,983,991,997]; 472 function get_random_prime(count,exclude,all_different){ // 個數, 排除 473 var _f=arguments.callee,i,j,p=[],l; 474 if(!count||count<1)count=1; 475 if(!_f.excluded) 476 _f.excluded=[]; 477 if(exclude)exclude=[]; 478 479 for(j=0;j<count;j++){ 480 l=80; // timeout 481 do{ 482 i=Math.round(10*Math.tan(Math.random()*1.5)); 483 if(!--l)return; // timeout 484 }while(_f.excluded[i]); 485 p.push(_f.primes[i]); 486 if(exclude)exclude.push(i); 487 } 488 489 // 選完才排除本次選的 490 if(exclude) 491 for(j=0,l=exclude.length;j<l;j++){ 492 i=exclude[j]; 493 if(_f.excluded[i])_f.excluded[i]++; 494 else _f.excluded[i]=1; 495 } 496 497 return count==1?p[0]:p; 498 } 499 500 // return [GCD, n1, n2, ..] 501 get_random_prime.get_different_number_set=function(count,till,GCD_till){ 502 delete this.excluded; 503 if(!GCD_till)GCD_till=1e5; 504 if(!till)till=1e5; 505 506 var GCD=get_product(this(20,1),GCD_till),na=[],n_e=[],n,i=0,out; 507 n_e[GCD]=1; 508 509 for(;i<count;i++){ 510 out=80; // timeout 511 do{ 512 n=this(20); 513 n.unshift(GCD); 514 n=get_product(n,till); 515 }while(n_e[n]&&--out); 516 n_e[n]=1; 517 na.push(n); 518 } 519 520 if(typeof lcm=='function') 521 na.LCM=lcm(na); 522 na.GCD=GCD; 523 return na; 524 }; 525 526 527 528 CeL.data.math 529 . 530 /** 531 * VBScript has a Hex() function but JScript does not. 532 * @param {Number} number 533 * @return {String} number in hex 534 * @example 535 * alert('0x'+CeL.hex(16725)) 536 */ 537 hex = function(number) { 538 return (number < 0 ? number + 0x100000000 : number - 0).toString(16); 539 } 540 541 CeL.data.math 542 . 543 /** 544 * 補數計算。 545 * 正數的補數即為自身。若要求得互補之後的數字,請設成負數。 546 * @param {Number} number 547 * @return {Number} base 1: 1's Complement, 2: 2's Complement, (TODO: 3, 4, ..) 548 * @example 549 * alert(complement()) 550 * @see 551 * http://www.tomzap.com/notes/DigitalSystemsEngEE316/1sAnd2sComplement.pdf 552 * http://en.wikipedia.org/wiki/Method_of_complements 553 * http://en.wikipedia.org/wiki/Signed_number_representations 554 * @since 2010/3/12 23:47:52 555 */ 556 complement = function() { 557 return this.from.apply(this, arguments); 558 }; 559 560 _.complement.prototype = { 561 562 base : 2, 563 564 // 1,2,.. 565 bits : 8, 566 567 // radix complement or diminished radix complement. 568 // http://en.wikipedia.org/wiki/Method_of_complements 569 diminished : 0, 570 571 /** 572 * 正負符號. 573 * 正: 0/false, 574 * 負 negative value:!=0 / true 575 */ 576 sign : 0, 577 578 // get the value 579 valueOf : function() { 580 return this.sign ? -this.value : this.value; 581 }, 582 583 /** 584 * set value 585 */ 586 set : function(value) { 587 var m = Number(value), a = Math.abs(m); 588 if (isNaN(m) || m && a < 1e-8 || a > 1e12){ 589 library_namespace.debug('complement.set: error number: ' + value); 590 return; 591 } 592 593 this.sign = m < 0; 594 // this.value 僅有正值 595 this.value = a; 596 597 return this; 598 }, 599 600 601 /** 602 * input 603 */ 604 from : function(number, base, diminished) { 605 // 正規化 606 number = ('' + (number||0)).replace(/\s+$|^[\s0]+/g, '') || '0'; 607 //library_namespace.debug(number + ':' + number.length + ',' + this.bits); 608 609 // 整數部分位數 610 var value = number.indexOf('.'), tmp; 611 if (value == -1) 612 value = number.length; 613 // TODO: not good 614 if (value > this.bits) 615 //throw 'overflow'; 616 library_namespace.err('complement.from: overflow: ' + value); 617 618 if (typeof diminished === 'undefined') 619 // illegal setup 620 diminished = this.diminished; 621 else 622 this.diminished = diminished; 623 624 if ((base = Math.floor(base)) && base > 0){ 625 if (base === 1) 626 base = 2, this.diminished = 1; 627 this.base = base; 628 }else 629 // illegal base 630 base = this.base; 631 //library_namespace.debug(base + "'s Complement"); 632 633 // TODO: 僅對 integer 有效 634 value = parseInt(number, base); 635 tmp = Math.pow(base, this.bits - 1); 636 if (value >= tmp * base) 637 //throw 'overflow'; 638 library_namespace.err('complement.from: overflow: ' + value); 639 640 //library_namespace.debug('compare ' + value + ',' + tmp); 641 if (value < tmp) 642 this.sign = 0; 643 else 644 //library_namespace.debug('負數 ' + (tmp * base - (diminished ? 1 : 0)) + '-'+ value+'='+(tmp * base - (diminished ? 1 : 0) - value)), 645 this.sign = 1, 646 value = tmp * base - (diminished ? 1 : 0) - value; 647 648 this.value = value; 649 //library_namespace.debug(number + ' → '+this.valueOf()); 650 651 return this; 652 }, 653 654 /** 655 * output 656 */ 657 to : function(base, diminished) { 658 if (!(base = Math.floor(base)) || base < 1) 659 base = this.base; 660 else if (base === 1) 661 base = 2, diminished = 1; 662 if (typeof diminished === 'undefined') 663 diminished = this.diminished; 664 665 var value = this.value, tmp = Math.pow(base, this.bits - 1); 666 if (value > tmp || value === tmp && (diminished || !this.sign)) 667 //throw 'overflow'; 668 library_namespace.err('complement.to: overflow: ' + (this.sign ? '-' : '+') + value); 669 670 if (this.sign){ 671 tmp *= base; 672 if (diminished) 673 // TODO: 僅對 integer 有效 674 tmp--; 675 //library_namespace.debug('負數 ' + value + ',sum=' + tmp); 676 // 負數,添上兩補數之和 677 value = tmp - value; 678 } 679 680 //library_namespace.debug('value: ' + (this.sign ? '-' : '+') + value); 681 682 value = value.toString(Math.max(2, this.base)); 683 684 return value; 685 } 686 687 }; 688 689 _.complement.prototype.toString = _.complement.prototype.to; 690 691 692 /* 693 ↑Math --------------------------------------------------------------- 694 */ 695 696 697 698 699 return ( 700 CeL.data.math 701 ); 702 } 703 704 705 }); 706 707