Implement cycle(...values) — given several values, return a function that hands back the next value every time you call it, looping forever once it runs off the end. Think of a playlist set to repeat: track 1, track 2, track 3, then back to track 1. The values you pass are fixed; the position advances on each call and wraps around. Each call to cycle(...) produces its own independent stepper — calling one never affects another.
// values: any[] — zero or more values to rotate through.
// returns: () => any
// A function. Each call returns the next value in order, wrapping
// from the last value back to the first. With NO values passed,
// the returned function returns undefined on every call.
function cycle(...values): () => any;
const next = cycle('a', 'b', 'c');
next(); // → 'a'
next(); // → 'b'
next(); // → 'c'
next(); // → 'a' (wrapped back to the start)
// Two independent cyclers — they do not share a position.
const a = cycle(1, 2);
const b = cycle(1, 2);
a(); // → 1
a(); // → 2
b(); // → 1 (b started fresh; a's calls didn't move it)
cycle(obj)() returns the same obj, not a copy.null, and undefined are all valid rotation members and must come back unchanged.cycle(...) call is independent. Two cyclers built from separate calls track separate positions; interleaving calls to them must not interfere.cycle() returns a function that returns undefined on every call and never throws.