4.7 KiB
id, title, challengeType, forumTopicId, dashedName
| id | title | challengeType | forumTopicId | dashedName |
|---|---|---|---|---|
| 5eb3e4a21f462f409d656c73 | 自参照序列 | 1 | 385317 | self-referential-sequence |
--description--
There are several ways to generate a self-referential sequence. One very common one (the Look-and-say sequence) is to start with a positive integer, then generate the next term by concatenating enumerated groups of adjacent alike digits:
0, 10, 1110, 3110, 132110, 1113122110, 311311222110 ...
生成的项在长度上几何增长并且永不收敛。
另一种生成自引用序列的方法是总结前一项。
计算每个相似数字有多少,然后将每个排序的枚举数字的总和和数字连接起来。 请注意,前五个术语与前面的序列相同。
0, 10, 1110, 3110, 132110, 13123110, 23124110 ...
将数字从大到小排序。 不包括上一项中未出现的数字计数。
根据种子值,以这种方式生成的序列总是收敛到稳定值或短周期模式。 (就我们的目的而言,收敛意味着一个元素与之前看到的元素匹配。) 所示序列的种子值为 0,经过 11 次迭代后收敛到稳定值 1433223110。 收敛最快的种子值为 22。 它在第一个元素之后稳定。 (下一个元素是 22,之前已经看到过。)
--instructions--
编写一个函数,将种子值作为参数,生成一个自引用序列直到它收敛,并将其作为数组返回。
--hints--
selfReferential 应该是一个函数。
assert(typeof selfReferential === 'function');
selfReferential(40) 应该返回一个数组。
assert(Array.isArray(selfReferential(40)));
selfReferential(40) 应该返回 ["40", "1410", "142110", "14123110", "1413124110", "2413125110", "151413224110", "152413225110", "251413324110", "152423224110", "152413423110"]。
assert.deepEqual(selfReferential(40), [
'40',
'1410',
'142110',
'14123110',
'1413124110',
'2413125110',
'151413224110',
'152413225110',
'251413324110',
'152423224110',
'152413423110'
]);
selfReferential(132110) 应该返回 ["132110", "13123110", "23124110", "1413223110", "1423224110", "2413323110", "1433223110"]。
assert.deepEqual(selfReferential(132110), [
'132110',
'13123110',
'23124110',
'1413223110',
'1423224110',
'2413323110',
'1433223110'
]);
selfReferential(132211) 应该返回 ["132211", "132231", "232221", "134211", "14131231", "14231241", "24132231", "14233221"]。
assert.deepEqual(selfReferential(132211), [
'132211',
'132231',
'232221',
'134211',
'14131231',
'14231241',
'24132231',
'14233221'
]);
selfReferential(1413223110) 应该返回 ["1413223110", "1423224110", "2413323110", "1433223110"]。
assert.deepEqual(selfReferential(1413223110), [
'1413223110',
'1423224110',
'2413323110',
'1433223110'
]);
selfReferential(251413126110) 应该返回 ["251413126110", "16151413225110", "16251413226110", "26151413325110", "16251423225110", "16251413424110", "16153413225110"]。
assert.deepEqual(selfReferential(251413126110), [
'251413126110',
'16151413225110',
'16251413226110',
'26151413325110',
'16251423225110',
'16251413424110',
'16153413225110'
]);
--seed--
--seed-contents--
function selfReferential(n) {
}
--solutions--
function selfReferential(n) {
var descending,
i,
incr,
j,
max_i,
max_len,
max_seq,
seq,
sequence,
indexOf =
[].indexOf ||
function(item) {
for (var i = 0, l = this.length; i < l; i++) {
if (i in this && this[i] === item) return i;
}
return -1;
};
sequence = function(n) {
var c, cnt, cnts, d, digit, i, j, l, len, new_cnts, ref, s, seq;
cnts = {};
ref = n.toString();
for (j = 0, len = ref.length; j < len; j++) {
c = ref[j];
d = parseInt(c);
incr(cnts, d);
}
seq = [ref];
while (true) {
s = '';
for (i = l = 9; l >= 0; i = --l) {
if (cnts[i]) {
s += '' + cnts[i] + i;
}
}
if (indexOf.call(seq, s) >= 0) {
break;
}
seq.push(s);
new_cnts = {};
for (digit in cnts) {
cnt = cnts[digit];
incr(new_cnts, cnt);
incr(new_cnts, digit);
}
cnts = new_cnts;
}
return seq;
};
incr = function(h, k) {
if (h[k] == null) {
h[k] = 0;
}
return (h[k] += 1);
};
descending = function(n) {
var tens;
if (n < 10) {
return true;
}
tens = n / 10;
if (n % 10 > tens % 10) {
return false;
}
return descending(tens);
};
return sequence(n);
}