Skirtumas
Pitmaster apskaičiuoja git vieninguoju formatu pateikiamus skirtumus. Skirtumų modulis palaiko kelis algoritmus, vieningąjį formatavimą, dvejetainių failų aptikimą ir rekursinį palyginimą medžių lygmeniu.
Pakeistam tekstiniam failui, kurio režimas 100644, format() sukuria tuos pačius baitus kaip git diff. Kiti atvejai šiuo metu formatuojami kitaip (#3):
- Nauji ir ištrinti failai neturi
new file mode/deleted file modeeilutės,indexeilutės ir/dev/null: abi pusės žymimosa/<path>irb/<path>, o tuščios pusės hunk intervalas užrašomas kaip-1,0arba+1,0, kai git užrašo-0,0arba+0,0. indexeilutė visada baigiasi100644, nepriklausomai nuo failo režimo.- Vien režimo pakeitimai (pavyzdžiui,
chmod +x) nesukuria rezultato. - Dvejetainiai failai pateikia
Binary files differbeindexeilutės, o git pateikiaBinary files a/<path> and b/<path> differ. - Pervadinimai rodomi kaip vienas
diff --git a/<old> b/<new>įrašas su turinio skirtumu, besimilarity index,rename fromarrename toeilučių.
Skirtumų operacijos
Nepatvirtinti pakeitimai (darbinis medis ir indeksas)
$diffs = $repo->diff();
foreach ($diffs as $diff) {
echo $diff->format();
}
Palygina kiekvieną indekso failą su jo dabartine būsena darbiniame medyje. Aptinka pakeitimus, ištrynimus ir dvejetainius failus.
Paruošti pakeitimai (indeksas ir HEAD)
$diffs = $repo->diffStaged();
foreach ($diffs as $diff) {
echo $diff->format();
}
Palygina dabartinį indeksą su HEAD įrašo medžiu. Parodo, kas bus įtraukta į kitą įrašą. Ištrinti ir pridėti failai su panašiu turiniu pateikiami kaip vienas pervadintas įrašas. Prieš pirmąjį įrašą HEAD nėra, todėl rezultatas tuščias (#5).
Šiuo metu pervadinimų poravimas taip pat susieja nesusijusius vienos eilutės failus, nes pabaigos tuščia eilutė laikoma bendru turiniu (#4).
Medžių palyginimas
$a = $repo->readObject($repo->resolve('HEAD~1')->hex)->tree;
$b = $repo->head()->tree;
$diffs = $repo->diffTree($a, $b);
Rekursyviai palygina du medžius. Perduokite medžių ID: įrašų ID nepaverčiami jų medžiais, todėl gaunamas tuščias rezultatas. Tą patį TreeDiff modulį naudoja diffStaged(), show() ir logPath().
Filtruoti pagal kelią
$diffs = $repo->diff('src/specific-file.php');
Kelio specifikacija yra tikslus failo kelias. diffStaged() priima tą patį argumentą, bet šiuo metu jo nepaiso, todėl visada grąžina visus paruoštus failus (#5).
Pasirinkti algoritmą
$diffs = $repo->diff(null, 'patience');
$diffs = $repo->diffStaged(null, 'histogram');
$diffs = $repo->diffTree($a, $b, 'minimal');
Galiojantys pavadinimai: myers (numatytasis), patience, histogram ir minimal. Bet kuris kitas pavadinimas sukelia InvalidArgumentException.
DiffResult struktūra
Kiekvienas DiffResult atspindi vieno failo skirtumą.
use Pitmaster\Diff\DiffResult;
foreach ($diffs as $diff) {
echo $diff->oldPath; // Path in the old tree
echo $diff->newPath; // Path in the new tree
echo $diff->binary; // true for binary files
echo $diff->oldHash; // Hex hash of the old blob (null for added files)
echo $diff->newHash; // Hex hash of the new blob (null for deleted files)
foreach ($diff->hunks as $hunk) {
echo $hunk->header(); // @@ -1,5 +1,7 @@
foreach ($hunk->lines as $line) {
echo $line . "\n"; // ' context', '+added', '-removed'
}
}
}
Suformatuota išvestis
echo $diff->format();
Sukuria vieningąją skirtumų išvestį. Pakeistam tekstiniam failui ji atitinka git diff:
diff --git a/src/File.php b/src/File.php
index abc1234..def5678 100644
--- a/src/File.php
+++ b/src/File.php
@@ -10,6 +10,8 @@ class File
private string $name;
+ private int $count;
+
public function __construct()
{
Tikrinti, ar yra pakeitimų
if ($diff->hasChanges()) {
// File was modified (or is binary with changes)
}
Hunk struktūra
Kiekvienas Hunk atspindi gretimą pakeitimų sritį su konteksto eilutėmis.
use Pitmaster\Diff\Hunk;
$hunk->oldStart; // Starting line in old file
$hunk->oldCount; // Number of lines from old file
$hunk->newStart; // Starting line in new file
$hunk->newCount; // Number of lines in new file
$hunk->lines; // Array of diff lines (prefixed with ' ', '+', or '-')
$hunk->header(); // "@@ -10,6 +10,8 @@"
Skirtumų algoritmai
Pitmaster įgyvendina keturis skirtumų algoritmus. Numatytasis yra Myers.
Myers skirtumas
Standartinis O(ND) algoritmas, toks pat kaip numatytasis git algoritmas. Sukuria minimalius redagavimo scenarijus.
use Pitmaster\Diff\MyersDiff;
$hunks = MyersDiff::diff($oldContent, $newContent);
diff() metodas priima dvi eilutes ir grąžina Hunk objektų masyvą. Įvestį jis suskaido pagal naujas eilutes, apskaičiuoja trumpiausią redagavimo scenarijų ir sugrupuoja pakeitimus į hunk blokus su 3 konteksto eilutėmis (kaip numatyta git).
Kantrybės skirtumas
Sukuria geresnius struktūrinius kodo skirtumus. Pirmiausia sulygina unikalias eilutes, tada užpildo tarpus tarp jų.
use Pitmaster\Diff\PatienceDiff;
$hunks = PatienceDiff::diff($oldContent, $newContent);
Histogramos skirtumas
Kantrybės skirtumo variantas, geriau apdorojantis pasikartojančias eilutes. Naudoja JGit ir Eclipse.
use Pitmaster\Diff\HistogramDiff;
$hunks = HistogramDiff::diff($oldContent, $newContent);
Minimalus skirtumas
Sukuria mažiausią įmanomą skirtumą (su mažiausiai pakeistų eilučių), tačiau skaičiavimas užtrunka ilgiau.
use Pitmaster\Diff\MinimalDiff;
$hunks = MinimalDiff::diff($oldContent, $newContent);
Dvejetainių failų aptikimas
Pitmaster turinį laiko dvejetainiu, jei tarp pirmųjų 8192 baitų yra NUL baitas (git tikrina pirmuosius 8000).
if (MyersDiff::isBinary($content)) {
// Binary file, skip line-level diff
}
Dvejetainiai failai sukuria DiffResult su $binary = true ir tuščiu $hunks masyvu. Suformatuota išvestis:
diff --git a/image.png b/image.png
Binary files differ
Spalvota išvestis
CLI terminalo išvestyje naudoja ColorDiff ANSI spalvas.
use Pitmaster\Diff\ColorDiff;
$colorized = ColorDiff::colorize($diff->format());
echo $colorized;
- Pridėtos eilutės (
+) rodomos žaliai - Pašalintos eilutės (
-) rodomos raudonai - Hunk antraštės (
@@) rodomos žydrai - Failų antraštės (
diff --git,index,---,+++) rodomos paryškintai
pitmaster diff visada nuspalvina išvestį, net kai ji perduodama per dujotiekį. pitmaster show nuspalvina tik tada, kai stdout yra terminalas.
Medžių skirtumas (vidinis)
TreeDiff klasė rekursyviai palygina du medžio objektus ir sukuria po DiffResult kiekvienam pakeistam failui.
use Pitmaster\Diff\TreeDiff;
$treeDiff = new TreeDiff($repo->objectDatabase());
$diffs = $treeDiff->diff($oldTreeId, $newTreeId);
Medžių skirtumo apdorojimas:
- Pridėti failai (yra tik naujame medyje)
- Ištrinti failai (yra tik sename medyje)
- Pakeisti failai (tas pats kelias, skiriasi blob maiša)
- Rekursinis poaplankių palyginimas
- Ištrintų ir pridėtų failų poravimas pervadinimams (tiksli maiša arba bent 50% bendrų eilučių)
Įrašai, kurių maiša nepasikeitė, praleidžiami, todėl vien režimo pakeitimas rezultato nesukuria.
Žodžių skirtumas
Skirta eilučių viduje esantiems žodžių lygmens pakeitimams.
use Pitmaster\Diff\WordDiff;
$result = WordDiff::diff('the quick fox', 'the slow fox');
// 'the [-quick-]{+slow+} fox'