19. Some examples of the smn theorem Example 19.1. For any x, we

19. Some examples of the s-m-n theorem
Example 19.1. For any x, we know that f (y) = ϕx (ϕx (y)) is computable, by substitution. So f = ϕi for
some i. The s-m-n theorem tells us how to find that i from x.
Let h(x, y) = ϕx (ϕx (y)). We know this is computable by the enumeration theorem: let g be the function
from the enumeration theorem with g(e, x) = ϕe (x); then we can build h(x, y) = g(x, g(x, y)) by substitution.
Then by the s-m-n theorem, there is a total computable function s with ϕs(x) (y) = h(x, y) = ϕx (ϕx (y)).
So given x, s(x) is the i we are looking for.
Example 19.2. For any x, we know that f (y) = ϕx (y 54 + 12) is computable, by substitution. So f = ϕi for
some i. The s-m-n theorem tells us how to find that i from x.
Let h(x, y) = ϕx (y 54 +12). We know this is computable by the enumeration theorem: let g be the function
from the enumeration theorem with g(e, x) = ϕe (x); then we can build h(x, y) = g(x, y 54 +12) by substitution.
Then by the s-m-n theorem, there is a total computable function s with ϕs(x) (y) = h(x, y) = ϕx (y 54 + 12).
So given x, s(x) is the i we are looking for.
Example 19.3. For any x, we know that the constant function f (y) = x is computable. So f = ϕi for some i.
The s-m-n theorem tells us how to find that i from x.
Let h(x, y) = x. We know this is computable because it’s one of the basic primitive recursive functions.
Then by the s-m-n theorem, there is a total computable function s with ϕs(x) (y) = h(x, y) = x.
So given x, s(x) is the i we are looking for.
20. The recursion theorem
Every time we build a computable function f , that function has a number i with f = ϕi . In fact, the point
of the padding theorem is that it has many numbers; our listing ϕ0 , ϕ1 , ϕ2 , . . . contains lots of repetition.
After we build a function, we could take the time to study it and figure out exactly what a number for it is;
this would be a long process, but we could do it.
Sometimes, however, it would be convenient if we could go the other direction; instead of building the
function and then finding a number for it, it would be nice if we could know a number for the function we’re
about to build before we build it. Then we could use that number in the process of building the function.
Keep in mind that a number for a function gives us a description for it; we can take that number and
figure out what Turing machine it corresponds to, which gives us a sort of description for the function and
how it was built. In most areas of mathematics, trying to get a description of something before you build
it would sound ridiculous, but in computability theory it’s possible. It will turn out to be a consequence of
the next theorem.
Theorem 20.1 (The recursion theorem). For any total computable function f , there is an n with ϕn = ϕf (n) .
Important: this is not saying n = f (n). For example, f (x) = x + 1 is a total computable function, and
there is no n with n = n + 1. But the theorem does tell us there are n with ϕn = ϕn+1 . Again, this is
because our listing of computable functions contains repetition.
Proof. Let h(u, x) = ϕϕu (u) (x). This doesn’t entirely make sense, because ϕu (u) might not converge, so
what would ϕϕu (u) be? So actually we mean
ϕϕu (u) (x) if ϕu (u)↓,
h(u, x) =
↑
otherwise.
Then h is computable. An algorithm for it is:
(1) On input (u, x), first run ϕu (u). Wait for it to converge.
(2) If ϕu (u) eventually gives an output, run ϕϕu (u) (x). Wait for it to converge.
(3) If ϕϕu (u) (x) eventually gives an output, output that.
Lines (1) and (2) are actually applications of the enumeration theorem. Let g be the function from the
enumeration theorem. Then line (1) actually means we should run g(u, u). Line (2) means we should run
g(g(u, u), x). In fact, we could write h succinctly as h(u, x) = g(g(u, u), x).
Now apply the s-m-n theorem to h to get a total computable function s with ϕs(u) (x) = h(u, x). Now
consider f ◦ s. This is a computable function, so there must be some v with f ◦ s = ϕv . Also, ϕv must be
total, since both f and s are. Let n = s(v).
I claim that this is the n we want. First note that since ϕv is total, ϕv (v)↓, so h(v, x) = ϕϕv (v) (x). For
any x, consider
ϕn (x)
=
ϕs(v) (x)
=
h(v, x)
=
ϕϕv (v) (x)
=
ϕf (s(v)) (x)
=
ϕf (n) (x).
So ϕn = ϕf (n) .
Example 20.2. Define
x if y = x,
↑ otherwise.
You can check that h is computable. Now apply the s-m-n theorem to get a total computable f with
ϕf (x) (y) = h(x, y). By the recursion theorem, there is an n with ϕn = ϕf (n) . So
n if y = n,
ϕn (y) =
↑ otherwise.
h(x, y) =
So dom(ϕn ) = {n}.
Example 20.3. Define h(x, y) = x. You can check that h is computable. Now apply the s-m-n theorem to
get a total computable f with ϕf (x) (y) = h(x, y). By the recursion theorem, there is an n with ϕn = ϕf (n) .
So ϕn (y) = n, meaning ϕn is the constant n function.
The above examples are what we meant by saying that a function knew it’s own number and used that
number in its construction. ϕn is defined in terms of n, so it’s as if we already knew n before we started
building ϕn . In general, when we want to build a function and know its number ahead of time, we can follow
this pattern:
(1) Define h(x, y) = something, treating y as the input variable and treating x as if it were the number
we wish we already knew.
(2) Apply the s-m-n theorem.
(3) Apply the recursion theorem.
Since we can build a function while already knowing its number, you might think we could use that to
make something deliberately different from itself. All that happens then is we get a function which does not
converge.
Example 20.4. Define h(x, y) = ϕx (y) + 1. This is computable by the enumeration theorem. Now apply the
s-m-n theorem to get a total computable f with ϕf (x) (y) = h(x, y). By the recursion theorem, there is an n
with ϕn = ϕf (n) . So for any y, ϕn (y) = ϕn (y) + 1. So ϕn (y) must diverge for all y.
21. Rice’s theorem
As mentioned in the last section, our numbering of computable functions ϕ0 , ϕ1 , ϕ2 , . . . contains lots of
repetition. You might just think this means we chose a bad numbering system. Couldn’t we take our current
system, but skip the repeats? In turns out this is impossible, because it’s very hard to tell if two computable
functions ϕi and ϕj are actually the same function.
Definition 21.1. A set A ⊆ N is an index set if it has the property that for all i, j ∈ N, if ϕi = ϕj and
i ∈ A, then j ∈ A.
In other words, for a computable function f , if A takes one number for f , A must take them all.
Example 21.2. The following are all index sets:
2
• N.
• ∅.
• Tot = {i | ϕi is total}.
• Inf = {i | dom(ϕi ) is infinite}.
• Ax = {i | ϕi = ϕx }.
In general, {i | “some property of ϕi that doesn’t mention i”} is an index set.
Theorem 21.3 (Rice’s theorem). The only computable index sets are ∅ and N.
Proof. Suppose A were a computable index set which is neither N nor ∅. We are going to build a computable
function that will lead to a contradiction. The idea is that this computable function will already know its
own number, so it can ask if that number is in A. If so, it will then copy a function which is not in A. If
not, it will copy a function which is in A. Either way, we get a contradiction.
Since A is not N, there is some i 6∈ N. Since A is not ∅, there is some j ∈ A. Since A is computable, χA
is computable. Consider the function h(x, y) defined as
ϕi (y) if χA (x) = 1,
h(x, y) =
ϕj (y) if χA (x) = 0.
Apply the s-m-n theorem and then the recursion theorem to get an n with ϕn (y) = h(n, y).
If n ∈ A, then χA (n) = 1, so ϕn = ϕi . But i 6∈ A, and A is an index set, which is a contradiction.
If n 6∈ A, then χA (n) = 0, so ϕn = ϕj . But j ∈ A, and A is an index set, which is a contradiction.
Either way we get a contradiction, so there cannot be a computable index set other than N or ∅.
Corollary 21.4. Tot and Inf (from the example above) are not computable.
Corollary 21.5. A padding function will not get us all the numbers for a computable function.
Proof. Consider Ax from the example above. Then Ax is not computable.
So let g be a computable padding function, and define h(y) = g [y] (x). Then h is a strictly increasing total
function, so its range is a computable set. So its range cannot be Ax . By definition, range(h) ⊆ Ax , so there
must be a y with ϕx = ϕy , but y 6∈ range(h).
So if we start from x and repeatedly apply padding, we will always miss something.
3