40

バージョン管理履歴を保存するための新しいweaveベースのデータ構造に取り組んでいます。これは間違いなく、それが出てきたときにそれが物事を行う正しい方法であるかどうかについていくつかの宗教戦争を引き起こすでしょうが、それは今の私の質問ではありません.

私の質問は、出力の責任と関係があります与えるべきです。コード行が何度も追加、削除、およびマージされた場合、どのリビジョンが原因であるかが常に明確であるとは限りません。これは特に、コードのセクションが削除されると、そこにあったすべての記録が失われ、削除の責任がないことを意味します。私がこの問題について話し合った人は皆、より良くしようとすることは単に価値がないと言っています. 削除されたセクションの後の行の責任が、実際のセクションが削除されたときのリビジョンに変更されたというハックを入れることがあります。おそらく、セクションが最後にある場合、最後の行の非難が変更され、ファイルが空になった場合、文字通り非難情報を置く場所が残っていないため、非難は実際にエーテルに消えます。

私の実際の質問に移ります。通常、各行のせいで、履歴で追加および削除された場所の完全な履歴を調べ、3方向マージ (または、十字型マージの場合はランダムでたらめ) を使用し、それらの間の関係に基づいて履歴に基づいて行が存在する必要があるかどうかを判断し、そうでない場合は、現在のリビジョンで新規としてマークします。異なる責任を持つ複数の祖先で行が発生する場合、継承するものを任意に選択します。繰り返しになりますが、この完全に文書化されていないが事実上の標準的な慣行を継続することは、議論の余地がないと思います。

私の新しいシステムが分岐するところは、履歴全体の複雑な計算に基づいて特定の行現在のリビジョンに含まれるかどうかの複雑な計算を行うのではなく、直接の祖先を調べ、その行がいずれかの行にあるかどうかです。非難を継承する任意のものを選択します。私は主に技術的な理由でこの変更を行っています (同様の技術的な理由と配慮の欠如により、他の Blame 実装が同じことを行う可能性は十分にあります) が、それについて考えた後、私の一部は実際には新しい動作を好むようになりました。古いものよりも直感的で予測可能です。みんなどう思う?

4

3 に答える 3

35

私は実際にそこにある非難の実装の1つを書きました(誰かが過去1、2年でそれを置き換えない限り、Subversionの現在のものだと思います)。他にも何人か手伝いました。

少なくとも非難のほとんどの実装は、あなたが説明したことをしません:

通常、各行のせいで、履歴のどこで追加および削除されたかの完全な履歴を調べ、3方向マージ (または、交差マージの場合はランダムのでたらめ) を使用し、それらの間の関係に基づいて、履歴に基づいて行が存在する必要があるかどうかを判断し、存在しない場合は、現在のリビジョンで新規としてマークします。異なる責任を持つ複数の祖先で行が発生する場合、継承するものを任意に選択します。繰り返しになりますが、この完全に文書化されていないが事実上の標準的な慣行を継続することは、議論の余地がないと思います。

実際、ほとんどの非難はこれよりもはるかに複雑ではなく、関係をまったく使用しようとはしませんが、単純なデルタ構造 (通常、以前に使用した差分アルゴリズムと同じ内部構造) を使用して、任意の順序で親をたどります。チャンクが変更されたかどうかを確認し、変更された場合はそれを非難し、その行を完了としてマークします。

たとえば、Mercurialは、すべての行が非難されるまで、反復的な深さ優先検索を実行します。関係が正しいものを非難する可能性が低いかどうかを考慮に入れようとはしません.

Gitはもう少し複雑なことを行いますが、それでも、あなたが説明したようなものではありません。

Subversion は Mercurial と同じことを行いますが、ヒストリー グラフは非常に単純なので、さらに簡単です。

次に、あなたが提案していることは、実際には、それらすべてが実際に行うことです:

任意の先祖を選び、それが完了するまでウサギの穴を下ってその道をたどります。すべての行を非難しない場合は、次の先祖を任意に選び、すべての非難が割り当てられるまで続行します。

于 2012-12-29T04:32:54.493 に答える
11

個人的なレベルでは、単純化されたオプションを好みます。

理由:ともかく非難はあまり使わない。

したがって、それを包括的に実装するために多くの時間を無駄にする意味はないと思います。

それは本当です。Blame は、「虹の果てにある金の壷」機能の 1 つであることがほとんど判明しています。ファイルをクリックするだけで、誰がどの行のコードを書いたかを確認できる日を夢見て、地面に立っている私たちにとって、それは本当にクールに見えました. しかし、それが広く実装されるようになった今、私たちのほとんどは、それが実際にはあまり役に立たないことに気付くようになりました. blameStack Overflow でタグのアクティビティを確認してください。それは圧倒的に荒涼としたものです。

私はここ数ヶ月だけでも、何十もの「非難に値する」シナリオに出くわしました。ほとんどの場合、最初に非難を使おうとしましたが、面倒であるか、まったく役に立たないことがわかりました。代わりに、問題のファイルに対して単純なフィルター処理された変更ログを実行することで、必要な情報を見つけました。場合によっては、Blame を使用して情報を見つけることもできましたが、それにはもっと時間がかかりました。

主な問題は、コードの書式設定の変更です。ほとんどすべての第一層の責任者は...私としてリストされていました!なんで?私は、改行とタブの修正、関数の順序の再ソート、関数の個別のユーティリティ モジュールへの分割、コメントの誤字の修正、コード フローの改善または簡素化を担当しているためです。そして、それが私でなければ、他の誰かが途中で空白またはブロック移動を行っていました. 非難の助けを借りずに私がすでに思い出すことができる前にさかのぼる何かについて意味のある非難を得るために、私は改訂をロールバックして再非難しなければなりませんでした. そしてまた責める。そしてまた。

したがって、最も幸運な状況以上に、非難が実際に時間の節約になるためには、非難がヒューリスティックに改行、空白、および理想的にはコピー/移動の変更をブロックすることができなければなりません。これは非常に難しい注文のように思えます。特に単一のファイルの変更ログを精査する場合は、ほとんどの場合、とにかく多くの差分が生成されず、手動でかなり迅速にふるいにかけることができます。(注目すべき例外は、おそらく、コードの 90% が 1 つまたは 2 つの巨大なファイルに詰め込まれている、不適切に設計されたソース ツリーです... しかし、最近の共同コーディング環境で、その多くを行っているのは誰でしょうか?)。

結論: 一部の人々は「それは非難できる!」と見たいので、非難の必要最小限の実装を与えてください。機能リストに。そして、重要なことに移ります。楽しみ!

于 2012-12-29T04:24:10.333 に答える
0

行マージ アルゴリズムは、開発者よりも愚かです。彼らが同意しない場合、それは決定点を示すのではなく、合併が間違っていることを示しているだけです. したがって、単純化されたロジックは実際にはより正確なはずです。

于 2012-12-29T05:35:08.540 に答える