Ця відповідь є офіційним доказом відповіді TheNumberOne , перерахуйте дійсні програми Brainf ** k , де може бути важко зрозуміти точні моменти, чому перерахування є правильним. Поняття нетривіального, чому не існує недійсної програми, яка відображає число, не охоплене дійсною програмою.
У цьому розділі великі літери використовуються для позначення програм, а невеликі змінні використовуються для функцій та цілих чисел. ~ - оператор конкатенації.
Пропозиція 1:
Нехай функцією f є програма, описана у цій відповіді. Тоді для кожної програми U існує дійсна програма V така, що f (U) = f (V)
Визначення 1:
Нехай g (X) - це число, [
яке відображається в програмі X, і h (X) - число, ]
яке з'являється.
Визначення 2:
Визначте P (x) такою функцією:
P(x) = "" (the empty program) when x <= 0
P(x) = "]" when x = 1
P(x) = "]]" when x = 2
etcetera
Визначення 3:
Враховуючи програму X, позначте X1 як її найбільший префікс [
символів, X2 - її центр, а X3 - найбільший суфікс ]
символів.
Доказ пропозиції 1:
Якщо g (U) = h (U), то U є дійсною програмою, і ми можемо взяти V = U. (тривіальний випадок).
Якщо g (U) <h (U), то ми можемо створити V заздалегідь [
символами n = h (U) - g (U) . Очевидно, f (V) = f (U), оскільки всі [
символи в префіксі видалені.
Тепер розглянемо g (U)> h (U). Визначте T = U2 ~ U3. якщо g (T) <= h (T), то ми можемо побудувати V, видаливши n = g (U) - h (U) [
символи.
Тож можна припустити, що h (T) <g (T). Побудуйте V = T ~ P (g (T) - h (T)).
Для продовження нам потрібні три невеликі факти:
Пункт 1: g (U2) = g (T)
U3 не містить жодних [
символів за своїм визначенням. Оскільки T = U2 ~ U3, всі його [
символи містяться в першій частині.
Спосіб 2: h (U3) <g (T)
Це випливає із зауваження, що h (T) <g (T) і h (U3) <h (U3 ~ U2) = h (T).
П. 3: h (V3) = g (U2) - h (U2)
h(V3) = h(U3) + g(T) - h(T) using the construction of V
h(V3) = h(U3) + g(U2) + g(U3) - h(U2) - h(U3) apply the definition of T
h(V3) = g(U2) - h(U2) *one term cancels, g(U3) is always zero, as U3 contains only `]` symbols*
Тепер покажемо, що f (V) = f (U).
f(U) = U2 ~ P(h(U3) - g(U2)) = U2 claim 2, definition of P
f(V) = U2 ~ P(h(V3) - g(V2))
= U2 ~ P(h(V3) - g(U2))
= U2 ~ P(g(U2) - h(U2) - g(U2)) claim 3
= U2 ~ P(-h(U2))
= U2 definition P
Це завершує доказ. QED
Зробимо також унікальність.
Пропозиція 2:
Нехай U, V - дві різні, дійсні програми. Тоді f (U)! = F (V)
Це досить просто в порівнянні з попередньою пропозицією.
Припустимо, що U2 = V2. Але тоді єдиний спосіб U та V може бути різним - додавання або вилучення n [
та ]
символів до U1 та U3 відповідно. Однак це змінює вихід f, оскільки f буде рахувати кількість невідповідних ]
символів у суфіксі.
Таким чином U2! = V2.
Очевидно, це призводить до суперечності. Оскільки U2 і V2 буквально містяться у висновках f (U) і f (V) відповідно, вони не можуть відрізнятися, за винятком "краю", місця, де U2 з'єднується з U3. Але перший і останній символи U2 і V2 не можуть бути [
або ]
за визначенням, тоді як це єдині символи, дозволені в U1, U3, V1, V3 відповідно і відповідно знову. Таким чином отримуємо U2 = V2. QED