如何创build一个函数,将一个数字转换为一个双hex数字?

也许我在math方面还不够好,但是在将数字转换为纯字母forms的单体Hexavigesimal时遇到问题,就像Microsoft Excel / OpenOffice Calc一样。

这里是我的代码版本,但没有给我我需要的输出:


     var toHexvg = function(a){
      var x ='';
      var let =“_ abcdefghijklmnopqrstuvwxyz”;
      var len = let.length;
      var b = a;
      var cnt = 0;
      var y = Array();
     做{
       A =(A-(一%LEN))/ LEN;
       CNT ++;
      }而(一个!= 0)
      A = B;
      var vnt = 0;
     做{
       B + = Math.pow((LEN),VNT)* Math.floor(A / Math.pow((LEN),VNT + 1));
       VNT ++;
      }而(VNT!= CNT)
      var c = b;
     做{
       y.unshift(c%len);
       C =(C-(C%LEN))/ LEN;
      }而(C!= 0)
      for(var i in y)x + = let [y [i]];
      return x;
     }

我的努力可以得到的最佳输出是: abcd ... yz ba bb bc – 虽然不是上面的实际代码。 预期的输出是假设是abc ... yz aa ab ac ... zz aaa aab aac ... zzzzz aaaaaa aaaaab ,你得到的图片。

基本上,我的问题更多的是做“math”而不是function。 最终我的问题是:如何在Hexavigesimal转换中的math,直到一个[假设]的无穷大,就像Microsoft Excel。

如果可能的话,一个源代码,提前谢谢。

好的,这是我的尝试,假设你想要序列以“a”(代表0)开始,并且要:

 a, b, c, ..., y, z, aa, ab, ac, ..., zy, zz, aaa, aab, ... 

这工作,希望有一定道理。 时髦的线是在那里,因为它在math上更有意义的0代表空string,然后“a”将是1,等等

 alpha = "abcdefghijklmnopqrstuvwxyz"; function hex(a) { // First figure out how many digits there are. a += 1; // This line is funky c = 0; var x = 1; while (a >= x) { c++; a -= x; x *= 26; } // Now you can do normal base conversion. var s = ""; for (var i = 0; i < c; i++) { s = alpha.charAt(a % 26) + s; a = Math.floor(a/26); } return s; } 

但是,如果您打算按顺序打印出来,则有更有效的方法。 例如,使用recursion和/或前缀和东西。

虽然@ user826788已经发布了一个工作代码(甚至更快),但我会发布我自己的工作,我在find这里的post之前(因为我不知道单词“hexavigesimal”)。 但是它也包含了相反的function。 请注意,我使用a = 1,因为我使用它来转换起始列表元素

 aa) first ab) second 

 <ol type="a" start="27"> <li>first</li> <li>second</li> </ol> 

 function linum2int(input) { input = input.replace(/[^A-Za-z]/, ''); output = 0; for (i = 0; i < input.length; i++) { output = output * 26 + parseInt(input.substr(i, 1), 26 + 10) - 9; } console.log('linum', output); return output; } function int2linum(input) { var zeros = 0; var next = input; var generation = 0; while (next >= 27) { next = (next - 1) / 26 - (next - 1) % 26 / 26; zeros += next * Math.pow(27, generation); generation++; } output = (input + zeros).toString(27).replace(/./g, function ($0) { return '_abcdefghijklmnopqrstuvwxyz'.charAt(parseInt($0, 27)); }); return output; } linum2int("aa"); // 27 int2linum(27); // "aa" 

我不明白如何从一个公式中解决这个问题,但是我用了一段时间,并且想出了下面的algorithm来从字面上计算出所需的列数:

 var getAlpha = (function() { var alphas = [null, "a"], highest = [1]; return function(decNum) { if (alphas[decNum]) return alphas[decNum]; var d, next, carry, i = alphas.length; for(; i <= decNum; i++) { next = ""; carry = true; for(d = 0; d < highest.length; d++){ if (carry) { if (highest[d] === 26) { highest[d] = 1; } else { highest[d]++; carry = false; } } next = String.fromCharCode( highest[d] + 96) + next; } if (carry) { highest.push(1); next = "a" + next; } alphas[i] = next; } return alphas[decNum]; }; })(); alert(getAlpha(27)); // "aa" alert(getAlpha(100000)); // "eqxd" 

演示: http : //jsfiddle.net/6SE2f/1/

highest数组保存当前最高数字,每个“数字”具有一个数组元素(元素0是最不重要的“数字”)。

当我开始上述时,如果再次请求相同的值,caching每个值似乎是一个好主意,以节省时间,但实际上(使用Chrome),只需要大约3秒钟来计算第1,000,000个值( bdwgn )约20秒计算第10,000,000个值( uvxxk )。 随着caching的删除,花了大约14秒的第10,000,000的价值。

刚刚在今天早些时候完成了这个代码 ,我发现这个问题,而寻求什么来命名该死的东西。 在这里(如果有人想使用它):

 /** * Convert an integer to bijective hexavigesimal notation (alphabetic base-26). * * @param {Number} int - A positive integer above zero * @return {String} The number's value expressed in uppercased bijective base-26 */ function bijectiveBase26(int){ const sequence = "ABCDEFGHIJKLMNOPQRSTUVWXYZ"; const length = sequence.length; if(int <= 0) return int; if(int <= length) return sequence[int - 1]; let index = (int % length) || length; let result = [sequence[index - 1]]; while((int = Math.floor((int - 1) / length)) > 0){ index = (int % length) || length; result.push(sequence[index - 1]); } return result.reverse().join("") } 

a代表0z代表25 。 所以z之后的数字是26 ,即1*26 + 0 ,所以ba是正确的。 ( zzzzz之后的zzzzzbaaaaa 。)