git - Git分支, fork , fetch , 合并, rebase 和克隆的区别是什么?

  显示原文与译文双语对照的内容

有人能帮助我理解分支,分支和Git中的克隆之间的区别?

同样,当我做 git fetch 而不是 git pull 时,这意味着什么?

同样,rebasemerge 相比意味着什么?

如何将个人提交到一起?

如何使用,为什么使用它们,以及它们代表什么?

GitHub中的图形是如何?

时间:

克隆只是仓库的副本。 表面上,它的结果相当于 svn checkout,在那里你可以从其他存储库下载源代码。 像Subversion和DVCSs这样的集中式版本控制的区别在于 Git,当你克隆时,你实际上正在复制整个源代码库,包括所有历史和分支。 现在你的机器上有了一个新的存储库,并且你所做的任何提交都进入了仓库。 在你将这些提交到另一个仓库( 或者原始的那个) 之前,任何人都不会看到任何更改,或者直到有人从你的仓库提交提交,如果它是公共可以访问的。

分支是存储库中的东西。 从概念上讲,它代表了一个开发线程。 你通常有一个主分支,但是你也有一个分支,在那里你正在处理某些功能 xyz,另一个用于修复 Bug abc 。 在question,当你已经签出一个分支,进行任何提交都会停留在这个分支,并不会与其他分支共享,直到你将它们用或者变基他们拖到 branch. 当然,对于分支来说,Git看起来有点奇怪,直到你看一下分支如何实现的底层模型。 我不是自己解释( 我已经说过太多了,methinks ),而是链接"计算机科学"解释Git模型如何分支和提交,从Git网站获取:

http://eagain.net/articles/git-for-computer-scientists/

fork不是一个Git概念,它更像是一个政治/社会概念。 也就是说,如果有些人对项目的运行方式不满意,那么他们可以使用源代码,并自己独立于原始开发者。 这将被视为一个分叉。 因为大家都已经有自己的Git使得分叉容易"母版"的源代码副本,因此它很简单,只需要切割的领带与最初的项目开发人员,并且不需要导出历史记录用SVN从共享存储库( 与你所要做的。

于更多的现代定义使用的地图"fork"information,编辑:由于我没有注意到相关的durrant还通过GitHub网站,如,请看一下批注和迈克尔回答下面验证该

Git

我的答案包括了很多人都问过的问题。

本地存储库

git ( 本地) 有一个目录(. git ),你将文件提交到它,这是你的'本地存储库'。 这与svn这样的系统不同,你可以在其中添加并提交到远程仓库。

git保存通过保存整个文件而改变的文件的每个版本。 这也与svn不同,因为你可以转到任何单独的版本,而不需要通过增量改变。

git根本不'锁定'文件进而避免了为一个编辑( 像pvc这样的旧系统)'独占锁'功能,所以总是可以被编辑,即使off-line所有文件。 它实际上是一个惊人的工作一起( 在同一个文件中) 拉出或者提取操作期间/合并文件的更改推送到远程存储库,如库托管。 只有当两个更改涉及同一行代码时,你才需要手动更改( 实际编辑一个文件) 。


分支

分支允许你保留主代码('主'分支),复制( 一个新分支),然后在新分支中工作。 完成后,将分支中所做的更改合并到主存储库。 许多组织对每个工作都使用分支,不管它是一个特性,Bug 还是工作项。 其他组织只使用分支进行主要更改,比如版本升级。 使用分支控制和管理分支,而在使用分叉的情况下,其他人控制着代码。
总的来说,有两种主要的方法来做分支。 第一种方法是在主分支上保留大多数更改,只使用分支的分支和longer-running之类的分支,这样你想有两个分支可以用于不同的需求。 第二个问题是,你基本上为每个特性请求 make Bug 修复或者琐事创建分支,然后手工决定什么时候将这些分支合并到主主分支。 虽然这听起来很乏味,但这是一种常用的方法,是我目前使用和推荐的一种,因为它保持了主分支清理器的功能,因此,我们只需要完成的代码,通过分支合并并合并分支。

使分支"中"成为一个分支的标准方法是做一个 merge 。 分支也可以是 rebase 到'清理'的历史。 它并不影响当前状态,并且是为了给出一个'清洗器'历史。 基本上你是从一个点( 通常来自主) 分支的。 因为你的'母版'本身已经向前移动了。 所以如果你在一个分支中所做的所有更改都是针对最近的主主机进行的,并且所有的修改都是针对最新的主机。 因此,流程是:保存更改;获取"新建"主控形状,然后再次重新应用更改。 请注意,与合并一样,rebase也会导致冲突,你必须手动解析( 编辑) 。

一个'指南'要注意:如果分支是本地的,并且你还没有将它推送到远程,那么只需要英镑 ! 这主要是因为rebasing可以改变其他人所看到的历史,这可能包括他们自己的提交。

跟踪分支

这些是名为 origin/branch_name ( 与branch_name相对应)的分支。 当你将代码推放到远程仓库的代码时,这实际上是发生的机制。 例如当你 git push 一个分支称为'building_groups',你的分支将首先转到原点/building_groups然后发到远程存储库( 那是一个 over-simplification,但现在足够好了)的。 类似地,如果你执行 git fetch building_groups,则检索到的文件将放置在你的原始/building_groups分支中。 然后你可以选择将这里分支合并到本地副本中。 我们的做法是总是做一个 git fetch 和手工合并而不是一个 git pull ( 这两个步骤在一个步骤中) 。

Fetch 新分支。

获取新分支:在克隆的初始点,你将拥有所有分支。 但是,如果其他开发人员添加分支并将它们推送到远程,需要有一个方法来'知道'的分支和它们的名称,以便能够在本地拉出它们。 这是通过一个 git fetch 完成的,它将使用跟踪分支将所有新的和已经更改的分支使用到本地存储库中( 例如。 原点/) 。一旦 Fetch 成功,一个可以 git branch --remote 列出跟踪分支和 git checkout [branch],实际上是 switch 。

合并

合并是合并来自不同分支或者同一分支( 例如当一个本地分支和远程连接不同步时。)的不同版本的代码更改的过程。 如果已经在分支中开发了工作,并且工作已经完成,那么可以准备并测试,然后将它合并到 master 分支。 这是通过 git checkout master 将 switch 到 master 分支,然后 git merge your_branch 。 合并将把所有不同的文件和 ,甚至不同的修改,在同一个文件中。 这意味着它实际上会改变文件内部的代码来合并所有的修改。 在执行 checkoutmaster 时,也建议执行 git pull origin master 获取将远程主机合并到本地主机的最新版本。 如果远程主机更改,换句话说,moved forward,你将看到反映在 git pull 期间的信息。 最重要的的"新建"master,如果遇到这种情况你建议以 git checkout your_branch 和然后 rebase 它通过掌握,以便所做的更改得到实际( 主控形状已经更改) 然后,你将继续获取最新的更新,如下一段所示。

如果没有冲突,那么master将在。 如果存在冲突,这意味着相同的文件在类似的代码行周围有更改,它不能自动合并。 在这种情况下,git merge new_branch 会报告有冲突。 你( 这两者都有变化)'解析'他们通过编辑文件,选择所需的更改时,实际上删除你不想要的线条变化,然后将该文件保存在。 这些更改用 ========<<<<<<<< 等分隔符标记

一旦你解决了任何冲突,你将再次 git addgit commit,这些更改继续合并( 在这个过程中,你将得到来自git的反馈来指导你) 。 当进程无法正常工作时,你会发现 git merge --abort 很容易重置。

交互式变量化和 squashing/reordering/removing 提交

如果你从事过的工作每天都在大量的小步骤,比如 你提交的代码作为'work-in-progress',你可能希望这些小的提交进入"壁球"较大体积的提交。 当你想与同事进行代码评审时,这一点尤其有用。 在一个commit,你不想重放所有的'步骤'你拍摄( 通过提交),你现在想要着重强调的是最终效果的我所有的改变对于这个( 差异) 之工作 在考虑是否要进行多次提交时,关键因素是多次提交是否针对同一个文件或者文件多次( 最好在这种情况下挤压提交) 。 这是用交互式的rebasing工具完成的。 这里工具允许你挤压提交,删除提交,重新提交消息,例如 等等 git rebase -i HEAD~10 注意,是 ~ 不是一个 - 造就了以下内容:
interactive rebasing in Git 请小心并使用这里工具'gingerly'。 一次执行一个 squash/delete/reorder,退出并保存该提交,然后重新输入该工具。 如果提交不是连续的,你可以重新排序它们( 然后按需要挤压) 。 实际上你也可以在这里删除提交,但是你确实需要确定你在做什么 !

叉子

在git仓库中有两种主要的协作方法。 首先,上面的细节是直接通过分支,人们从/到。 这些协作者在远程仓库注册了ssh密钥。 这将让他们直接推送到仓库。 缺点是你必须维护用户列表。 另一种方法- 分叉- 让任何人都可以'fork'存储库,基本上是在他们自己的git仓库账户中创建一个本地副本。 然后,它们可以进行更改,完成发送一个'请求请求'( 实际上它更多是来自它们的一个'推',并对实际存储库维护者发出一个'拉拉'请求) 来获得代码。
第二个方法,使用 fork,不需要有人维护存储库的用户列表。


GitHub

github ( 一个远程存储库) 是一个远程的源,如果你有( 或者被添加到) 这样的存储库,那么你通常会推并拉这些更改,所以本地和远程实际上是截然不同的。 另一种思考远程存储库的方法是它是一个. git 目录结构,它位于远程服务器上。

当你在github浏览器界面中'fork'时,你可以点击 enter image description here 在你 gitub代码。实在('克隆') account, - 你创建一个副本, 第一次做它可能有点微妙,所以一定要确保你的代码库在哪个仓库里列出了一个代码库( 原始所有者或者'派生自'以及你,e.g. ) enter image description here
一旦你拥有本地副本,你就可以根据需要进行更改。 当你完成之后,你将一个'请求请求'提交到原始仓库所有者/管理员( 听起来很别致,但实际上你只需要点击这里:- enter image description here ) 并将它的放入。
在一起处理代码的团队更常见的是'克隆'存储库( 点击'复制'icon 在档案库屏幕的主屏幕上) 。 然后,本地类型 git clone [paste] 将把你设置为本地,你也可以将它的推送到( 共享) github位置。

克隆

就像在github上的部分中指出的,克隆是存储库的副本。 当你有一个远程存储库,你会根据它的URL发出 git clone 命令,然后你就会得到一个本地副本,或者是存储库的克隆。 这个克隆体具有一切,这些文件,在主分支,其他的分部,现有的全部提交,将产生的整个表达式。 是这个克隆,你做了你的添加和提交,然后远程存储库本身就是你推动那些提交到。 这个本地/远程概念使得 git ( 和它类似的系统,比如 Mercurial ) 成为一个 DVCS ( 分布式版本控制系统),而不是更传统的( CVS版本控制系统的代码),比如 SVN,pvc,CVS,等等,你可以直接提交到远程仓库。

可视化效果

核心概念的可视化可以在下面看到
http://marklodato.github.com/visual-git-guide/index-en.html web
http://ndpsoftware.com/git-cheatsheet.html#loc=index

我叫'地铁地图'( esp,包含图形界面,如果希望在可视化工具的可视化显示所做的更改将如何工作,你是不能打 gitg 伦敦的Underground,伟大的展示了谁做了什么,如何改变,改变和合并等等。

你还可以使用它来添加,提交和管理你的更改 !

gitg/gitx interface

尽管 gitg/gitx是相当小的,在最后 2 -3年( 2009 -2012 ) 图形用户接口工具的数量在不断增多。 有一个直观且强大interface,许多苹果机用户使用叉 brotherbard gitx和用于Linux的一个伟大的选择是

smart-git GUI

注意,即使使用了一个gui工具,你也可能在 命令行 上执行很多命令。
为此,我的~/.bash_aliases 文件中有以下别名( 从 ~/.bashrc 文件调用每个终端会话的文件:


# git
alias gst='git status' # Warning: gst conflicts with gnu-smalltalk (when used).
alias gb='git branch'
alias gco='git checkout'
alias gcob='git checkout -b '
alias ga='git add '
alias gc='git commit'
alias gg='git grep ' # A great very FAST search option, easier then `find`

最后,5键 lifesavers:

1 ) 你搞乱了你的本地分支,只是想回到你上次做 git pull的时候:


git reset --hard origin/master # You will need to be comfortable doing this!

2 ) 你开始在本地进行更改,你可以编辑半打文件,然后,oh垃圾 crap,你仍然在主( 或者另一个或者) 分支中:


git checkout -b new_branch_name # just create a new branch
git add. # add the changes files
git commit -m"your message" # and commit them

3 ) 你将当前分支中的一个特定文件搞乱,并希望基本上将该文件'重设'作为最后一次从远程存储库中提取它的方式: git checkout your/directories/filename 这实际上会重置文件( 和许多git命令一样,它在这里所做的并不是很好) 。

4 ) 你在本地进行了一些更改,你想要确保在执行 git reset 或者rebase时不会丢失它们: 我经常手工复制整个项目( cp -r.. /my_project ~/ ) 当我不确定我是否会在git中崩溃或者丢失重要的更改时。

5 ) 你在不断的改变,但是事情会变得一团糟:


git rebase --abort # To abandon interactive rebase and merge issues

这里是所有这一切是如何结合在:奥利弗形象的Steele,

enter image description here

...