You start with a number. This is your input. You have bits you want to encode—a binary string. You also have parameters: c (how many times to iterate the CORE transform when you use it) and x (how many times to repeat each encoding step).
Take your current number. You're going to transform it x times.
If the bit is '1':
Repeat x times: - XOR the number with the next pseudo-random bits - Apply the CORE transform c times - The result becomes your new current number
If the bit is '0':
Repeat x times: - XOR the number with the next pseudo-random bits - The result becomes your new current number
That's it. Move to the next bit and repeat.
After processing all your bits, you have a final number. This is your output. You've encoded every bit from your binary string into the transformation path. Each bit you encoded saved you one bit of space.
You take the output number. You know the parameters c and x. You have the same pseudo-random bit source.
For each bit position you want to decode:
Repeat x times: - Attempt to apply the UNCORE transform c times - Check: did we reach the termination condition (2^n - 2)? - If yes, record success for this iteration - If no, record failure - Continue with the result (or the failed state) After x iterations: - If all x succeeded: the bit was '1' - If any failed: the bit was '0'
When you encoded '1', you applied CORE transforms. The UNCORE transform reverses these, reaching termination each time. When you encoded '0', you only XORed with random bits. The UNCORE transform has nothing to reverse—it's operating on randomness, which doesn't have the structure to reach termination.
The x repetitions ensure reliability. Random data might accidentally look like CORE-transformed data once. But x times in a row? The probability becomes negligible.
You've compressed your input by encoding bits. Each bit encoded saves one bit. The compression is real, and the encoded bits are recoverable with overwhelming probability when x is sufficiently large.