Notes by Richard O'Keefe
There are NP-hard problems which are of such practical importance that we can't just ignore them and hope they will go away.
In such a case, we have some alternatives:
Next lecture we shall look at clustering, which doesn't even try to find the most parsimonious tree.
Here are several examples of putting up with a bad worst case.
minimize cost.vars subject to A.vars = 0 vars all >= 0
That is, minimize (or maximise) a linear combination of some variables, subject to a set of linear equalities and inequalities on those variables, where all the variables are non-negative. For several decades, people happily used a method called the Simplex Method to solve these problems. In effect, the Simplex Method chooses a subset of the variables to be the "basis" and solves the equations for that basis, and moves from basis to basis along the edges of a simplex. The fact that there are exponentially many subsets of a given size is why the method has, in principle, exponential worst case cost. But in practice, the method took polynomial time on real problems. We got away with it. In the mid-70s Karmakar published his famous algorithm showing that the problem had a polynomial time solution, and we now have reasonably efficient algorithms with good worst case cost. In practice, the Simplex Algorithm is still a good thing to try, and because Bell Labs patented Karmakar's method there was a period where you had to use an exponential cost method despite knowing a polynomial time one existed because you weren't allowed to use the faster one!
The classical NP-complete problem is SAT. An atom is a propositional variable (it can be true or false). A literal is either an atom or an atom with a NOT in front of it. A clause is a set of literals: it is true if one of its atoms is true or one of its negated atoms is false. A SAT problem is a set of clauses, where we want an assignment of true/false to the variables which makes all of the clauses true at the same time.
In general, the cost of finding a solution is O(2n). I once worked with van Gelder, who was in a team of students who managed to get it down to about O(1.02m), but it's still exponential time.
In practice, people often use something called Binary Decision Diagrams. Basically, a BDD is just a graph where the leaves are false and true and the internal nodes are "if (some variable) then (left branch) else (right branch)". An Ordered BDD is one where no variable occurs more than once on a path to a leaf, and a Reduced ODBB is one where each subgraph is represented at most once. There are nice algorithms for making ROBDDs, and given the ROBDD for a Boolean formula you can just read off an assignment by walking up from the 'true' leaf. Any algorithm for solving Boolean problems must have exponential worst case, so ROBDDs must have exponential worst case. But they work well enough in practice to be used for problems with thousands of variables. (Provided that you are willing to put up with them occasionally bogging down.)
Another technique is a randomised technique called GSAT. Repeatedly, pick a random assignment and hill-climb. Each hill climbing step finds out how many more clauses would be true after flipping each variable, and greedily flips the variable that makes the biggest improvement. If hill climbing finds a solution, stop with that solution. If hill climbing stops, unable to find any improvement, go back and start with another random assignment. This approach too works well enough in practice to be useful for problems with thousands of variables. (An improved version of GSAT is called WalkSAT. Look it up.)