Dead code elimination Dead code sits there doing nothing, staring at us knowing it will never be executed... but today we can take revenge.
Specification
The input will be a multiline string.
Each line may either be an assignment or an expression .
Assignment
An assignment is of the form &lt;name&gt; = number where name is a sequence of letters, underscores and numbers, but not starting with a number.
Variables may be assigned any number of times.
Expression
An expression is of the form &lt;var_name OR number&gt; &lt;operation&gt; &lt;var_name OR number&gt; ...
An expression may be any combination of:

Variables already defined
Basic arithmetic operators +-*/
Numbers (integers)

Expected output
You should output the string with redundant assignments, assignments that are never used by any of the expressions following it, removed. Please note that assignments can also be made redundant if an additional assignment to the same variable is performed before an expression using the variable is executed.
Test cases
in
a = 10
a * 3

out
a = 10
a * 3


in
foo = 8
2 - 1
a = 18

out
2 - 1


in
a = 10
a = 8
b = 4
ab = 72  
b / 6
b + 1

out
b = 4
b / 6
b + 1


in
a = 1
a = 2
a + 1

out
a = 2
a + 1


in
FooBar1 = 0
Fuz__ = 8
Fuz__ / 1

out
Fuz__ = 8
Fuz__ / 1


in
a = 1
a + 1
a = 2
a + 1

out
a = 1
a + 1
a = 2
a + 1


in
a = 1
1 / 5 * 8 + 4

out
1 / 5 * 8 + 4


in
a = 1
a + 1
a = 1
a + 1

out
a = 1
a + 1
a = 1
a + 1


in
a = 7
5 / a

out
a = 7
5 / a
PHP - 197 bytes

The function works by analysing each line, in the reverse order and one after the other, and maintaining an array of the used variables.


If there is an equal character = in the line, it's an assignment.


It the variable is used, the assignment is useful, and the line is printed, but the variable isn't considered used any more.
Otherwise, do nothing.

Otherwise, the line is an expression. We split the line after each space, and add each symbol to the list of used variables. Numbers (1, 2, …) and operators (+, -, …) will be added too, but since they aren't valid variables names, it's not a problem. The line is then of course printed.




function($c){$u=[];foreach(array_reverse(split('
',$c))as$l){if($p=strpos($l,'=')){if(!isset($u[$x=substr($l,0,$p-1)]))continue;
unset($u[$x]);}else$u+=array_flip(split(' ',$l));$f="
$l$f";}echo$f;}


Here is the ungolfed version:

function removeDeadCode($code)
{
    $usedVariables = [];
    $finalCode = '';

    foreach (array_reverse(explode("\n", $code)) as $line)
    {
        if ($equalPosition = strpos($line, '='))
        {
            $variable = substr($line, 0, $equalPosition - 1);
            if (isset($usedVariables[$variable]))
            {
                $finalCode = "\n" . $line . $finalCode;
                unset($usedVariables[$variable]);
            }
        }
        else
        {
            $usedVariables += array_flip(explode(' ', $line));
            $finalCode = "\n" . $line . $finalCode;
        }
    }

    echo $finalCode;
}