Tengo esto que no funciona, para ciclos como 1 2 3 4 5 6 7 8 9 1 2 3 4 ... , ciclos entre 1 y 9.
const cycle = integers => { let i = 0 let x = integers[i++] while (i < integers.length) { let y = integers[i++] const s = x + y const remainder = (s % 9) + 1 x = remainder } return (x - 1) % 9 } logCycle([ 9, 6 ]) logCycle([ 9, 9 ]) logCycle([ 9, 9, 9, 9, 9 ]) logCycle([ 9, 129, 993, 91, 9 ]) logCycle([ 9, 10 ]) function logCycle(i) { log('cycle', i, cycle(i)) } function log(t, i, o) { console.log(`${t}(${JSON.stringify(i)}) => ${o}`) } Observe cómo en el cycle([9, 9]) devuelve 0, y en otros lugares también se descompone. La función de cycle toma una matriz de enteros, de longitud arbitraria. Entonces, la matriz puede tener 1000000 elementos, o solo 2.
Espero:
cycle([9, 9]) => 9cycle([9, 10]) => 1¿Cómo hago para que esto funcione correctamente? ¿Y cómo hago para que funcione para cualquier par de números mínimos/máximos, como si quisiera alternar entre (e incluyendo) 5 y 13, o 79 y 5337, cómo lo haría genérico así?
La función cycle está sumando y haciendo un módulo en el resultado, para que "ciclo" idealmente dentro de ese rango. No está iterando a través del ciclo, es "sumando a través del ciclo", como un reloj.
También busca mantener la solución no recursiva, ya que la cantidad de elementos en la array puede ser grande.
Aparentemente entendí mal algunas partes de la pregunta al principio. Después de haber leído aún más comentarios, me parece que
Para estos requisitos lo siguiente debería funcionar:
function defCycle(m,n){ const base=n-m+1,off=m-1; // base: sequence-length, off: offset of sequence return arr=>(arr.reduce((a,c)=>a+c)%base||base)+off; }; // run the function on a collection of test data: const ntest=1000000; [[1,9],[5,13],[79,5337]] .forEach(([m,n],cycle)=>{ console.log(`Sequence from ${m} to ${n}:`); cycle=defCycle(m,n); [[ 9, 6 ],[ 9, 9 ],[ 9, 9, 9, 9, 9 ],[ 9, 129, 993, 91, 9 ],[ 9, 10 ],[1, 811, 29317, 391, 21],[ntest*(ntest+1)/2]] .forEach(arr=>console.log(`cycle(${JSON.stringify(arr)}) => ${cycle(arr)}`)); console.log(`cycle([1,2,3,...,${ntest}]) => ${cycle([...Array(ntest)].map((_,i)=>i+1))}`); }); Los dos últimos casos de prueba deberían producir exactamente el mismo resultado: pasar por la suma de una matriz de secuencia de 1 a 1000000 ( = (1000000*1000001)/2) debería dar como resultado 1 (para la secuencia: "1... 9").
La acción dentro de la función defCycle() ocurre en estas dos líneas:
base=n-m+1,off=m-1;base : el número de elementos de secuenciaoff : el desplazamiento de la secuenciam=5,n=11 => base=7,off=4return arr=>(arr.reduce((a,c)=>a+c)%base||base)+off;base calculada previamente y off . El cálculo consta de las dos expresiones:[shift] = (arr.reduce((a,c)=>a+c) suma todos los elementos del arr pasado como argumento - y[shift]%base||base calcula el resultado real: el módulo(base) del total [shift] . Siempre que el resultado ==0 se reemplaza con el valor base .Si solo necesita el resultado (no es necesario realizar otras operaciones durante el ciclo), puede calcularlo con bastante facilidad utilizando la conversión base.
function getResult(base, num) { const str = (parseInt((num-1).toString(base)) + 1).toString() return str.charAt(str.length - 1) } console.log( getResult(9, 6) ) // 6 console.log( getResult(9, 9) ) // 9 console.log( getResult(9, 10) ) // 1