Git常见面试题30道

1、 Git如何找到特定提交中已更改的文件列表?

git diff-tree -r {hash} //-r 标志使命令列出单个文件

2、 Git 是用什么语言编写的?

  • 你需要说明使用它的原因,而不仅仅是说出语言的名称。我建议你这样回答:

Git使用 C 语言编写。 GIT 很快,C 语言通过减少运行时的开销来做到这一点。

3、 git中的“staging area”或“index”是什么?

For this answer try to explain the below diagram as you can see: 可以通过下图进行解释:在完成提交之前,可以在称为“staging area”或“index”的中间区域中对其进行格式化和审查。从图中可以看出,每个更改首先在暂存区域中进行验证,我将其称为“stage file”,然后将更改提交到存储库。

4、 git clone 和fork 的区别

git clone 是在将github上的代码克隆到本地

fork是在github上使用fork将别人的远程仓库复制一份到自己的远程仓库上。

5、 fork、 branch、clone 之间的区别?

fork:是对存储仓库(repository)进行的远程的,服务器端的拷贝。复刻不是git范畴。
clone:不是复刻,克隆是对某个远程仓库的本地拷贝。克隆时,实际上是拷贝整个存储仓库,包括所有的历史记录和分支。
branch:是一种机制,用于处理单一存储仓库中的变更,并最终目的是用于与其他部分代码合并。

6、 git功能分支操作


 
  1. master //默认的主分支
  2. git branch //查看本地分支
  3. git branch 分支名称 //新建分支
  4. git checkout 分支名称 //切换分支
  5. git checkout -b 本地分支名 //切换分支
  6. git checkout origin 远程分支名  //切换分支
  7. git branch -r //查看远程仓库的分支
  8. git push --set-upstream origin 分支名称 //本地分支提交到远程仓库
  9. git branch -d 分支名称 //删除本地分支
  10. git push origin --delete 分支名称 //删除远程仓库的分支

7、 git add . 和 git add * 区别

git add . 会把本地所有untrack的文件都加入暂存区,并且会根据.gitignore做过滤,但是git add * 会忽略.gitignore把任何文件都加入

8、 Git和SVN的区别

Git SVN
1. Git是一个分布式的版本控制工具 1. SVN 是集中版本控制工具
2.它属于第3代版本控制工具 2.它属于第2代版本控制工具
3.客户端可以在其本地系统上克隆整个存储库 3.版本历史记录存储在服务器端存储库中
4.即使离线也可以提交 4.只允许在线提交
5.Push/pull 操作更快 5.Push/pull 操作较慢
6.工程可以用 commit 自动共享 6.没有任何东西自动共享

9、 git revert和git reset的区别

reset用于回退版本,可以遗弃不再使用的提交。

reset用法基本一致,git revert 撤销某次操作,此次操作之前和之后的 commit和history都会保留,并且把这次撤销,作为一次最新的提交。

  • git revert是用一次新的commit来回滚之前的commit,git reset是直接删除指定的commit
  • git reset 是把HEAD向后移动了一下,而git revert是HEAD继续前进,只是新的commit的内容和要revert的内容正好相反,能够抵消要被revert的内容

10、 git 跟其他版本控制器有啥区别?

Git比svn快,而且更加的流畅。

Git在本地就可以使用,可以随便保存各种历史记录,不用担心污染服务器。

Git在branch和branch之间切换非常简单。

Git没有被lock不能commit 的情况。

11、 Git中 HEAD、工作树和索引之间的区别?

该工作树/工作目录/工作空间是你看到和编辑的(源)文件的目录树。

该索引/中转区(staging area)是个在 /.git/index,单一的、庞大的二进制文件,该文件列出了当前分支中所有文件的 SHA1 检验和、时间戳和文件名,它不是个带有文件副本的目录。

HEAD是当前检出分支的最后一次提交的引用/指针。

12、 git pull 和git fetch的区别

fetch + 合并 =pull

13、 git pull 和 git fetch 有什么区别? 

git pull命令从中央存储库中提取特定分支的新更改或提交,并更新本地存储库中的目标分支。

git fetch也用于相同的目的,但它的工作方式略有不同。当你执行git fetch时,它会从所需的分支中提取所有新提交,并将其存储在本地存储库中的新分支中。如果要在目标分支中反映这些更改,必须在git fetch之后执行git merge。只有在对目标分支和获取的分支进行合并后才会更新目标分支。

git pull = git fetch + git merge

14、 forking的工作流程的优点

它不是用单个服务端仓库充当“中央”代码库,而是为每个开发者提供自己的服务端库。forking工作流程最常用于公共开源项目中。
Forking工作流程的主要优点是可以汇集提交贡献,又无需每个开发者提交到一个中央仓库中,从而实现干净的项目历史记录。开发者可以推送代码到自己的服务端仓库,而只有项目维护人员直接推送代码到官方仓库中。
当开发者准备发布本地提交时,他们的提交会推送到自己的公共仓库中,而不是官方仓库中。
然后他们向主仓库请求拉取(pull request),这会告知项目维护人员由可以集成的更新。

15、 GitFlow工作流程分支有哪些

GitFlow可以用来管理分支。GitFlow工作流中常用的分支有下面几类:

master分支:最为稳定功能比较完整的随时可发布的代码,即代码开发完成,经过测试,没有明显的bug,才能合并到 master 中。请注意永远不要在 master 分支上直接开发和提交代码,以确保 master 上的代码一直可用;

develop分支;用作平时开发的主分支,并一直存在,永远是功能最新最全的分支,包含所有要发布 到下一个 release 的代码,主要用于合并其他分支,比如 feature 分支; 如果修改代码,新建 feature 分支修改完再合并到 develop 分支。所有的 feature、release 分支都是从 develop 分支上拉的。

feature分支;这个分支主要是用来开发新的功能,一旦开发完成,通过测试没问题(这个测试,测试新功能没问题),我们合并回develop 分支进入下一个 release

release分支;用于发布准备的专门分支。当开发进行到一定程度,或者说快到了既定的发布日,可以发布时,建立一个 release 分支并指定版本号(可以在 finish 的时候添加)。开发人员可以对 release 分支上的代码进行集中测试和修改bug。(这个测试,测试新功能与已有的功能是否有冲突,兼容性)全部完成经过测试没有问题后,将 release 分支上的代码合并到 master 分支和 develop 分支

hotfix分支;用于修复线上代码的bug。**从 master 分支上拉。**完成 hotfix 后,打上 tag 我们合并回 master 和 develop 分支。

16、 git config 的功能是什么?

git 使用用户名将提交与身份相关联。git config 命令可用来更改git 配置,包括用户名

例如:git config -global user.name "you name"

git config -global user.email "you email"

17、 Git常用命令

  • git show # 显示某次提交的内容 git show $id
  • git add # 将工作文件修改提交到本地暂存区
  • git rm # 从版本库中删除文件
  • git reset # 从暂存区恢复到工作文件
  • git reset HEAD^ # 恢复最近一次提交过的状态,即放弃上次提交后的所有本次修改
  • git diff # 比较当前文件和暂存区文件差异 git diff
  • git log -p # 查看每次详细修改内容的diff
  • git branch -r # 查看远程分支
  • git merge # 将branch分支合并到当前分支
  • git stash # 暂存
  • git stash pop #恢复最近一次的暂存
  • git pull # 抓取远程仓库所有分支更新并合并到本地
  • git push origin master # 将本地主分支推到远程主分支

18、 GitFlow主要工作流程

1.初始化项目为gitflow , 默认创建master分支 , 然后从master拉取第一个develop分支

2.从develop拉取feature分支进行编码开发(多个开发人员拉取多个feature同时进行并行开发 , 互不影响)

3.feature分支完成后 , 合并到develop(不推送 , feature功能完成还未提测 , 推送后会影响其他功能分支的开发);合并feature到develop , 可以选择删除当前feature , 也可以不删除。但当前feature就不可更改了,必须从release分支继续编码修改

4.从develop拉取release分支进行提测 , 提测过程中在release分支上修改BUG

5.release分支上线后 , 合并release分支到develop/master并推送;合并之后,可选删除当前release分支,若不删除,则当前release不可修改。线上有问题也必须从master拉取hotfix分支进行修改;

6.上线之后若发现线上BUG , 从master拉取hotfix进行BUG修改;

7.hotfix通过测试上线后,合并hotfix分支到develop/master并推送;合并之后,可选删除当前hotfix ,若不删除,则当前hotfix不可修改,若补丁未修复,需要从master拉取新的hotfix继续修改;

8.当进行一个feature时 , 若develop分支有变动 , 如其他开发人员完成功能并上线 , 则需要将完成的功能合并到自己分支上,即合并develop到当前feature分支;

9.当进行一个release分支时 , 若develop分支有变动 , 如其他开发人员完成功能并上线 , 则需要将完成的功能合并到自己分支上,即合并develop到当前release分支 (!!! 因为当前release分支通过测试后会发布到线上 , 如果不合并最新的develop分支 , 就会发生丢代码的情况);

GitFlow的好处

GitFlow为不同的分支分配一个明确的角色,并定义分支之间如何交互以及什么时间交互;可以帮助大型项目理清分支之间的关系,简化分支的复杂度。

19、 git中 HEAD、工作树和索引之间的区别

head:是当前检出分支的最后一次提交的引用或指针。
该索引/中转区(staging area)是个在/.git/index,单一的,庞大的二进制文件,该文件中列出了分支中所有文件的校验和,时间戳和文件名,它不是个带有文件副本的目录。
工作树/工作目录/工作空间是你看到的和编辑的(源)文件的目录树。

20、 Git恢复先前的提交

git reset –hard HEAD~1

21、 Git 中 HEAD、工作树和索引之间的区别?

  • 该工作树/工作目录/工作空间是你看到和编辑的(源)文件的目录树。
  • 该索引/中转区(staging area)是个在 /.git/index,单一的、庞大的二进制文件,该文件列出了当前分支中所有文件的 SHA1 检验和、时间戳和文件名,它不是个带有文件副本的目录。
  • HEAD是当前检出分支的最后一次提交的引用/指针。

22、 git reset、git revert 和 git checkout 有什么区别

这个问题同样也需要先了解 git 仓库的三个组成部分:工作区(Working Directory)、暂存区(Stage)和历史记录区(History)。

首先是它们的共同点:用来撤销代码仓库中的某些更改。

然后是不同点:

首先,从 commit 层面来说:

git reset 可以将一个分支的末端指向之前的一个 commit。然后再下次 git 执行垃圾回收的时候,会把这个 commit 之后的 commit 都扔掉。git reset 还支持三种标记,用来标记 reset 指令影响的范围:

–mixed:会影响到暂存区和历史记录区。也是默认选项;
–soft:只影响历史记录区;
–hard:影响工作区、暂存区和历史记录区。

注意:因为 git reset 是直接删除 commit 记录,从而会影响到其他开发人员的分支,所以不要在公共分支(比如 develop)做这个操作。

git checkout 可以将 HEAD 移到一个新的分支,并更新工作目录。因为可能会覆盖本地的修改,所以执行这个指令之前,你需要 stash 或者 commit 暂存区和工作区的更改。

git revert 和 git reset 的目的是一样的,但是做法不同,它会以创建新的 commit 的方式来撤销 commit,这样能保留之前的 commit 历史,比较安全。另外,同样因为可能会覆盖本地的修改,所以执行这个指令之前,你需要 stash 或者 commit 暂存区和工作区的更改。

然后,从文件层面来说:

git reset 只是把文件从历史记录区拿到暂存区,不影响工作区的内容,而且不支持 –mixed、–soft 和 –hard。

git checkout 则是把文件从历史记录拿到工作区,不影响暂存区的内容。

当执行git rm --cached命令时,会直接从暂存区删除文件,工作区则不会做出改变

当执行 git checkout . 或者 git checkout -- 命令时,会用暂存区全部或指定的文件替换工作区的文件。这个操作很危险,会清除工作区中未添加到暂存区的改动

当执行git checkout HEAD . 或者git checkout HEAD 命令时,会用HEAD指向的master分支中的全部或者部分文件替换暂存区以及工作区的文件。这个命令也是具有危险性的,因为不但会清除工作区中未提交的改动,也会清除暂存区中未提交的改动

git revert 不支持文件层面的操作。

回答关键点:

对于 commit 层面和文件层面,这三个指令本身功能差别很大。

git revert 不支持文件层面的操作。

不要在公共分支做 git reset 操作。

23、 git merge和git rebase的区别

git merge:保留提交记录,合并时会生成一个新的提交
git merge:保留提交记录,合并时不会生成一个新的提交

如果你想要一个干净的,没有merge commit的线性历史树,那么你应该选择git rebase
如果你想保留完整的历史记录,并且想要避免重写commit history的风险,你应该选择使用git merge

24、 git add和git stage的区别

在回答这个问题之前需要先了解 git 仓库的三个组成部分:工作区(Working Directory)、暂存区(Stage)和历史记录区(History):

工作区:在 git 管理下的正常目录都算是工作区,我们平时的编辑工作都是在工作区完成。

暂存区:临时区域。里面存放将要提交文件的快照。

历史记录区:git commit 后的记录区。

然后是这三个区的转换关系以及转换所使用的命令:

然后我们就可以来说一下 git add 和 git stage 了。其实,他们两是同义的,所以,惊不惊喜,意不意外?这个问题竟然是个陷阱…

引入 git stage 的原因其实比较有趣:

是因为要跟 svn add 区分,两者的功能是完全不一样的,svn add 是将某个文件加入版本控制,而 git add 则是把某个文件加入暂存区,因为在 git 出来之前大家用 svn 比较多,所以为了避免误导,git 引入了git stage,然后把 git diff –staged 做为 git diff –cached 的相同命令。基于这个原因,我们建议使用 git stage 以及 git diff –staged。

25、 Git什么操作会产生冲突,该怎么解决?

rebase:重新设置基准,然后应用补丁。

pull :会自动merge

repo sync :会自动rebase

cherry-pick :会应用补丁

没有更新代码就进行提交,覆盖别人的代码。

解决办法:一般就是创建一个新的冲突分支,在手动修改完成后在提交,push

26、 Git工作流程

  1. 在工作目录中修改某些文件
  2. 对修改后的文件进行快照,然后保存到暂存区域
  3. 提交更新,将保存在暂存区域的文件快照永久转储到Git目录中

27、 git add和git commit的区别

要想弄明白git add和git commit的区别,首先我们需要知道三个概念:工作区(Working Directory)、版本库(Repository)、暂存区(Stage or index)。

工作区

当你在开发一个项目时,主目录就是你的工作区。

版本库

工作区中有一个隐藏目录.git,这个就是git的版本库了。

暂存区

Git的版本库里存了很多文件,其中包括称为Stage或index的暂存区,还有一个git为我们自动创建的第一个分支master,以及指向master的一个指针HEAD。
下面就是三个区的示意图:图片来着廖雪峰老师的 博客。

三个区的示意图三个区的示意图

git add和git commit的区别就在于:

git add把文件添加进去,实际上就是把文件修改添加到暂存区;

git commit提交更改,实际上就是把暂存区的所有内容提交到当前分支。

因为我们创建Git版本库时,Git自动为我们创建了唯一一个master分支。所以,git commit就是往master分支上提交更改。

你可以简单理解为,需要提交的文件修改通通放到暂存区,然后,一次性提交暂存区的所有修改。

所以要想将修改提交到master中一定要先git add到暂存区中,再git commit到master分支。

28、 git和svn有什么联系和区别?

1.git是分布式的,svn是集中式的
2.git侧重命令,svn侧重界面(废话)

关于版本管理软件发展历程
① 文件备份
② 第一代版本管理软件:集中式、全量备份、版本迭代
以CVS软件为代表,这种管理方式已经过时,大部分项目中不再采用
优点:每次备份都是全量备份,基本不会出现文件丢失的问题
缺点:每次备份都是全量备份,导致服务器仓库需要大量的空间存储项目数据
③ 第二代版本管理软件:集中式、差异化备份、版本迭代
以SVN软件为代表,这种管理方式在现有的大部分项目中依然采用
优点:部署方便,命令简单,操作简洁
缺点:很久以前只能部署在局域网中(现在可以部署在广域网)、集中式(远程仓库一旦下线,版本管理方式就全部失效)、大量的版本管理问题
④ 第三代版本管理软件:分布式、差异化备份、版本迭代
以GIT软件为代表,这种管理方式在现有的大部分项目中组中主流的使用方式
优点:分布式(不依赖某个仓库、可以任意更新和提交)、基于网络(异地办公)
缺点:操作方式相对门槛较高

29、 git常用的命令有哪些?

  • git add 添加文件到暂存区
  • git commit 提交文件到本地仓库
  • git pull 从远程仓库拉取项目到本地
  • git push 将本地仓库的新的改变推送到远程仓库
  • git clone 将远程仓库复制到本地
  • git fetch 抓取
  • git merge 合并

30、 git rebase的作用?

场景:在公司开发忘记提交到github托管,在家里又继续开发新的功能,

然后到公司昨天的代码跟你的新功能合并的时候可以用git fecth ---> git rebase

那么他的提交记录就不会出现分叉,保持了提交记录的整洁.

你可能感兴趣的