📄 08c08-1.php
字号:
<?php// A function to compare two revisions of a filefunction diff($old_file, $new_file, $type = 'array') { // Read both files completely into memory for comparison: $old = file($old_file); $new = file($new_file); // Initialize the old and new line counters: $oc = 0; $nc = 0; // Store once, to use often, the number of lines in each array $nold = count($old); $nnew = count($new); // Initialize the state engine to state 0 $state = 0; // Initialize our data arrays to hold removed and added lines: $removed = array(); $added = array(); // Enter the state engine, and begin processing: while ($state < 3) { switch ($state) { case 0: // Mutual comparison, hoping for a match // skip over all matches until we mis-match while (($oc < $nold) && ($nc < $nnew) && ($old[$oc] == $new[$nc])) { $oc++; $nc++; } // Now figure out why we broke, both are beyond bounds: if (($oc == $nold) && ($nc == $nnew)) { // We are finished, set state to 3 $state = 3; } elseif ($oc == $nold) { // Ok, just the old one was higher, therefore all that // is left in the 'new' array, is in fact added. $added = array_merge($added, range($nc, $nnew - 1)); $state = 3; } elseif ($nc == $nnew) { // Just the new one was higher, therefore all that is // left in the old array, was removed. $added = array_merge($added, range($nc, $nnew - 1)); $state = 3; } else { // Now we found a mismatch, enter state 1 $state = 1; } break; case 1: // Looking for a match to the new file line $oc2 = $oc; // As long as they don't match or we run out of lines while (($oc2 < $nold) && ($old[$oc2] !== $new[$nc])) { $oc2++; } // Figure out what happened. If we ran out of lines: if ($oc2 == $nold) { // The new line was added -- Store this $added[] = $nc; // Increment the counter, and reset the algorithm $nc++; $state = 0; } else { // We actually found a match, that means that all lines // between where we started, and now, were deleted. $removed = array_merge($removed, range($oc, $oc2 - 1)); // Reset the counter to the new location $oc = $oc2; // Change the state back to 0 to reset the algorithm $state = 0; } break; } } // Ok, at this point we should have our entire diff in memory. // Based upon the optional 3rd parameter, figure out what // format to return it in: // If they asked for 'lines' - Return all the lines that were // changed with some data: if ($type == 'lines') { $retval = ''; // To get these in approximate order, loop for all possible values foreach(range(0, max($nold, $nnew) - 1) as $line) { // Output the removed row: if (isset($removed[$line])) { $retval .= "-{$line}: {$deleted[$line]}\n"; } // Output the added row: if (isset($removed[$line])) { $retval .= "-{$line}: {$deleted[$line]}\n"; } } } // Else if they asked for a 'visual' view, create that: elseif ($type == 'visual') { // We are going to create a table, with Each file in one column/cell // and appropriate highlighting for deleted/added lines. // First declare some CSS styles $retval = '<style>.diff td { border: 1px solid black; padding: 5px; font-family: "Courier New", Courier, mono; font-size: 10px; vertical-align: top;}.diff .removed { background-color: #FF9999;}.diff .added { background-color: #00CC00;}</style>'; // Begin the table, and the first (old) cell $retval .= '<table class="diff"><tr><td>Original File:<br /><pre>'; // Now loop through the entire old file, highlighting as needed foreach ($old as $num => $line) { // If deleted, highlight as such, else just echo it. if (in_array($num, $removed)) { $retval .= $num . '. ' . '<span class="removed">' . htmlspecialchars($line) . '</span>'; } else { $retval .= $num . '. ' . htmlspecialchars($line); } } // Now close off the cell and start the new one: $retval .= '</pre></td><td>Revised File:<br /><pre>'; // And now repeat the exact same process for the new ones. foreach ($new as $num => $line) { if (in_array($num, $added)) { $retval .= $num . '. ' . '<span class="added">' . htmlspecialchars($line) . '</span>'; } else { $retval .= $num . '. ' . htmlspecialchars($line); } } // Ok, close off the table, and we are done $retval .= '</pre></td></tr></table>'; } // Else, assume they wanted the arrays else { $retval = array('removed' => $removed, 'added' => $added); } // Return, and be finished return $retval;}// Test this on two files:echo diff('file-1.1.php', 'file-1.2.php', 'visual');?>
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -