Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

What exactly is the halting problem?

People also ask

What is the halting problem in simple terms?

unsolvable algorithmic problem is the halting problem, which states that no program can be written that can predict whether or not any other program halts after a finite number of steps. The unsolvability of the halting problem has immediate practical bearing on software development.

What does the halting problem tell us?

A machine with an oracle for the halting problem can determine whether particular Turing machines will halt on particular inputs, but they cannot determine, in general, if machines equivalent to themselves will halt.

What is halting problem explain with an example?

Example. ATM = {(M,w) | M is a TM and M halts at input w }. We can build a universal Turing machine which can simulate any Turing machine on any input. Suppose, if M goes into an infinite loop on input w, then the TM Recognize-ATM is going to run forever which means TM is only a recognizer, not a decider.

What is the theorem of halting problem?

In 1936, Alan Turing proved that the halting problem over Turing machines is undecidable using a Turing machine; that is, no Turing machine can decide correctly (terminate and produce the correct answer) for all possible program/input pairs.


EDIT (much later than original answer): MarkCC of Good Math, Bad Math recently wrote up an excellent discussion of the Halting problem with concrete examples.

The halting problem is basically a formal way of asking if you can tell whether or not an arbitrary program will eventually halt.

In other words, can you write a program called a halting oracle, HaltingOracle(program, input), which returns true if program(input) would eventually halt, and which returns false if it wouldn’t?

The answer is: no, you can’t.

Following up on questions about whether the input to the Halting problem is relevant or a red herring: Yes, the input is important. Also, there seems to be some confusion in that I see "infinite" being used where "arbitrary" is more correct.

Practical example: Imagine that you are working in a QA position and you are to write a halting checker program (aka an oracle) that will confirm that for any arbitrary program written by the development team (D) and any arbitrary input provided by the end-user (I), program D will eventually halt when given input I.

Cue manager voice: "Ho ho, those goofy users, let's make sure that no matter what garbage they type, our server tasks will never end up in an endless loop. Make it so, code monkey!"

This seems like a great idea, right? You don't want your server to hang, right?

What the halting problem is telling you is that you are being handed an unsolvable task. Instead, in this particular case, you need to plan for tasks that run past a threshold time and be ready to cancel them.

Mark uses code instead of input to illustrate the problem:

def Deciever(i):
  oracle = i[0]
  in = i[1]
  if oracle(Deceiver, i):
    while True:
      continue
  else:
    return i

In my discussion in the comments, I went the route of malicious input manipulation to force an unsolvable problem. Mark's example is far more elegant, using the halting oracle to defeat itself:

So, the input to Deceiver is actually a list of two elements: the first one is a proposed halting oracle. The second is another input. What the halting killer does is ask the Oracle: “Do you think I’ll halt for input i?”. If the oracle says, “Yes, you’ll halt”, then the program goes into an infinite loop. If the oracle says “No, you won’t halt”, then it halts. So no matter what the oracle says, it’s wrong.

Said another way, without cheating, reformatting inputs, countable / uncountable infinities or anything other distractions, Mark has written a piece of code that can defeat any halting oracle program. You cannot write an oracle that answers the question of whether Deceiver ever halts.

Original answer:

From the great Wikipedia:

In computability theory, the halting problem is a decision problem which can be stated as follows: given a description of a program and a finite input, decide whether the program finishes running or will run forever, given that input.

Alan Turing proved in 1936 that a general algorithm to solve the halting problem for all possible program-input pairs cannot exist. We say that the halting problem is undecidable over Turing machines. Copeland (2004) attributes the actual term halting problem to Martin Davis.

One of the critical points is that you have no control over either the program or the input. You are handed those and it's up to you to answer the question.

Note also that Turing machines are the basis for effective models of computability. Said another way, everything that you do in modern computer languages can be mapped back to these archetypical Turing machines. As a result, the halting problem is undecidable in any useful modern language.


To solve the halting problem, you'd have to develop an algorithm that could determine whether any arbitrary program halts for any arbitrary input, not just the relatively simple cases in your examples.


Here is a simple explanation of the proof that the halting problem is undecidable.

Assume you have a program, H, which computes whether or not a program halts. H takes two parameters, the first is a description of a program, P, and the second is an input, I. H returns true if P halts on input I, and false otherwise.

Now write a program, p2, which takes as it's input the description of another program, p3. p2 calls H(p3, p3), then loops if H returns true and halts otherwise.

What happens when we run p2(p2)?

It must loop and halt at the same time, causing the universe to explode.


This has been beaten to death so well that there is actually a poetic proof, written in the style of Lewis Carroll Dr. Seuss by Geoffrey Pullum (he of Language Log fame).

Funny stuff. Here's a taste:

Here’s the trick that I’ll use – and it’s simple to do.
I’ll define a procedure, which I will call Q,
that will use P’s predictions of halting success
to stir up a terrible logical mess.

...

No matter how P might perform, Q will scoop it:
Q uses P’s output to make P look stupid.
Whatever P says, it cannot predict Q:
P is right when it’s wrong, and is false when it’s true!


There's an OK proof the Halting Problem on wikipedia.

To illustrate, exactly, why just applying some technique to loops is insufficient, consider the following program (pseudocode):

int main()
{
  //Unbounded length integer
  Number i = 3;

  while(true)
  {
    //example: GetUniquePositiveDivisiors(6) = [1, 2, 3], ...(5) = 1, ...(10) = 1, 2, 5, etc.
    Number[] divisiors = GetUniquePositiveDivisiors(i);
    Number sum = 0;
    foreach(Number divisor in divisiors) sum += divisor;

    if(sum == i) break;

    i+=2;
  }
}

Can you think of an approach that will return true if this code halts, and false otherwise?

Think Carefully.

If by chance you're in serious contention for a Fields medal, imagine some code for these problems in place of the above.


"If you just add one loop, you've got the halting program and therefore you can't automate task"

Sounds like someone over generalizing the application of the halting problem. There are plenty of particular loops that you can prove terminate. There exists research that can perform termination checking for wide classes of programs. For instance in Coq you are limited to programs that you can prove terminate. Microsoft has a research project called Terminator that uses various approximations to prove that programs will terminate.

But, remember, the halting problem isn't just about toy examples. Neither of those solves the general 'halting problem', because they don't work for every program.

The problem is that the halting problem says that there exist programs that you have no way to know if they will terminate without running them, which means that you may never get done deciding if they halt.

An example of a program that may or may not halt (in Haskell):

collatz 1 = ()
collatz !n | odd n     = collatz (3 * n + 1)
           | otherwise = collatz (n `div` 2)

or in something more accessible:

while (n != 1)
    if (n & 1 == 1) 
        n = 3 * n + 1;
    else 
        n /= 2;

Given every integer >= 1, will this program halt? Well, it has worked so far, but there is no theorem that says it will halt for every integer. We have a conjecture due to Lothar Collatz that dates back to 1937 that it holds, but no proof.


Turing's great example was self-referential - Suppose there IS a program that can examine another one and determine whether or not it will halt. Feed the halting-program-checker ITSELF into the halting-program-checker - what should it do?