本文简单的记录一下Git的一些基本的概念和基础的操作,主要是弄懂基本的东西,能够快速的上手并开始使用;但是更多深层的原理和应用还是需要另外去进一步学习的。
我们先整一个git仓库,再来看看基本概念;
默认打开的地址是应该是用户目录,也就是c盘Users下某个地方,下面就先在固定的地址新建一个空的目录作为我们的新项目,叫做FastApiProject
:
$ pwd # 查看刚进入的时候地址
/c/Users/minch
$ cd / # 返回根目录
$ cd /D/Coding/GitHouse/ # 切换到存放项目的地址
$ mkdir FastApiProject # 新建一个文件夹
$ cd ./FastApiProject/ # 切换到新建的目录下
在项目目录下,输入git init命令初始化一个Git仓库;现在虽然创建好了,但是依旧是一个空的仓库,创建的时候也有提示;
$ git init
Initialized empty Git repository in D:/Coding/GitHouse/FastApiProject/.git/
经过了上面的操作,再看下面的就简单多了;
版本库也就是git仓库,Git 仓库是用于版本控制的一个特殊目录(.git目录
),它保存了项目的完整历史记录和元数据信息。Git 仓库存储了每个提交的快照,以及分支、标签、远程仓库等额外信息。Git 仓库是用于跟踪和管理项目中文件的更改的核心部分。
其实Git仓库就是一个文件夹,一个用来管理代码版本的文件夹。
Git 仓库对应一个存储库,它会记录每次对项目文件的修改。当您在 Git 仓库中进行更改时,Git 会跟踪这些变化并保存它们的历史记录。
这意味着,每当您在项目中添加、修改或删除文件时,Git 都会创建一个新的备份,称为提交(commit
)。提交是代码修改的快照,并包含了作者、时间戳以及相关的元数据信息。
通过这些提交,Git 可以帮助您追踪项目历史,查看特定版本的代码状态,甚至回滚到之前的某个状态。
.git
文件夹包含了记录代码历史和管理版本控制所需的所有信息。下面是.git
文件夹中常见的一些重要文件和文件夹:
objects
文件夹:存储Git对象,其中包括提交(commit)、树(tree)和Blob对象(即文件内容)。refs
文件夹:存储分支(branch)和标签(tag)引用的文件。例如,refs/heads
存储分支引用,refs/tags
存储标签引用。config
文件:包含了Git 仓库的配置选项,例如用户名、邮箱等。HEAD
文件:指向当前所在分支或提交的引用。index
文件:暂存区(stage)的索引文件,记录即将提交的文件变更信息。logs
文件夹:存储每次操作的日志信息,包括提交日志(commit logs)和引用日志(reflogs)。 .git
文件夹中的这些文件和文件夹(以及其他一些附加文件)共同组成了Git版本库的结构,保存了项目的完整历史记录和相关元数据信息。通过读取和操作.git
文件夹中的内容,Git可以进行版本控制、回溯历史、分支管理等操作。
现在其实就很好理解了,通常.git
文件夹会被放置在项目目录的根目录下。
在项目目录中执行git init
命令来初始化一个新的Git仓库时,Git会在当前目录创建.git
文件夹,并将其作为Git仓库的根目录。这意味着该文件夹将包含Git仓库的所有信息和元数据。
所以正常应用也大可不必想上面那样去创建项目,直接在项目根目录下运行命令即可;
git add
命令将所需更改添加到暂存区。添加到暂存区后,这些更改就准备好提交到本地仓库中。git diff
命令可以比较工作区和暂存区之间的差异,进一步清楚地了解即将提交的更改内容。这可以帮助检查更改是否符合预期,并在提交前进行必要的修改。git commit
命令将本地暂存区中的更改提交到本地仓库中时,Git会为该提交创建一个新的版本,并将其永久保存在本地仓库中,也就是上面提到的版本库。主要作用:
git commit
命令提交更改时,Git会为该提交创建一个新的版本,并将其永久保存在本地版本库中。通过本地版本库,您可以追溯代码的演变历史,查看每个提交的详细信息,并轻松地进行版本控制。git checkout
命令,您可以切换到不同的分支、标签或具体的提交。这非常有用,当您需要回退错误的更改、测试旧版本的功能或处理紧急问题时。git push
命令将本地版本库中的更改推送到远程仓库,并使用git pull
命令从远程仓库拉取最新的更改,可以与其他开发人员保持同步。git push
命令,您可以将本地仓库中的更改推送至远程仓库,以便与他人共享和协作。
add
:将工作区中的更改添加到本地暂存区。
commit
:将本地暂存区中的更改提交到地仓库,创建一个新的提交。
主要完成的内容就是创建一个新的提交,包括暂存区中的所有更改;每个提交都有一个唯一的哈希值,用于在版本历史中标识该提交。提交时,可以提供一条有意义的提交消息来描述更改的内容。
checkout
:用于在本地仓库中切换分支或恢复历史版本。
主要操作是将Git版本库中的内容拿到工作区。例如回退版本,连续两天提交了版本,第三天的时候,想要将工作区的内容回退到第一天提交的版本,就需要checkout操作回退版本。
或者从一个分支切换到另一个分支,分支的概念看下文;
clone
:克隆远程仓库到本地,创建一个本地仓库的副本。
克隆操作其实就是一个粘贴复制,把远程的仓库完整的拷贝到本地仓库;通常是包含两步:
git clone
命令,将远程仓库的内容复制到本地仓库中。克隆操作会自动将远程仓库的全部历史记录、分支信息和文件复制到新创建的本地仓库目录中,并为远程仓库设置一个别名(默认为“origin”)。push
:将本地仓库中的更改推送至远程仓库。
将本地的提交推送到远程仓库,更新远程仓库的分支和提交历史。
pull
:从远程仓库拉取最新更改(相当于fetch
+ merge
)。
其实也是两步;更新是从远程仓库(remote repository)到本地仓库(local repository),但实际的合并操作是将更改从本地仓库合并到工作区(working directory)和本地仓库的当前分支。
fetch
:从远程仓库获取最新的提交、分支和标签信息,但不会自动合并到本地分支。merge
:将获取的最新提交合并到当前分支中,以保持与远程仓库同步。总结一下,git
的流程涉及到四个位置,分别是工作区、暂存区、本地仓库、远程仓库;工作区就是项目目录,就是完整项目的根目录,暂存区和本地仓库都是git在本地工作涉及的两个位置,都位于项目目录下.git
目录下;其次是远程仓库,远程仓库就是类似GitHub、gitee
类的平台,其实就是互联网上的版本库;
完整的流程是新建一个项目,同时新建一个本地库,项目第一版部分代码开发完成后,提交代码到暂存区(add
),等本次开发完成了,就将暂存区打代码提交到本地仓库(commit
);发现有问题或者更新等需要切换版本的时候,就将本地仓库的内容回退到工作区(checkout
);本地仓库完成提交后,就可以将仓库信息给推送到远程仓库存储起来,有修改之后,继续推送到远程仓库(push
);另外的人想要接入项目,就从远程仓库克隆一下仓库,克隆到本地之后(clone
),经过checkout的操作就可以在工作区看到对应版本的代码了;整个流程打通了之后,远程仓库发生修改了,就可以将远程的修改拉回本地(pull
),实际也是拉回本地,进一步将版本切换到工作区;
大的流程如此,但是实际的使用过程还是相对复杂的,还涉及分支、合并等一系列的操作,但是理解这个基本流程后,后面的内容就都好理解了;
分支的创建和合并是版本控制系统中比较重要的操作,Git最初就是为了方便世界各地的Linux内核开发者设计的,就是要让分支的创建和合并变的简单而且安全。
分支的概念是比较好理解的,git的版本库就是由很多个分支组成的,我们不创建新的分支的时候,默认就是main/master
分支,也就是主分支,这个名称在安装的时候有提到过;
如果把每次commit
看作一个版本提交,那么上面图片中的每个节点都可以看作一个版本,分支就是在项目的当前状态上创建了一个完全一样的“副本”,这个副本可以独立进行修改,而不影响其他分支或主分支。
在这个新的分支上,可以随意修改代码、添加新的功能、调试和测试,而不会对主分支上的代码产生任何影响。这个分支与主分支相互独立,可以将其看作是一个完整的项目副本。
当在这个分支上进行开发工作时,其他人可以继续在主分支上进行工作,互不干扰。这就是Git分支的优势之一:团队成员可以并行开发不同的功能,而不会影响彼此的工作。
当完成了在分支上的开发工作并测试通过后,可以将这个分支合并回主分支,以将新的功能或修复应用到整个项目中。Git提供了合并分支的功能,它会将分支上所做的更改整合到主分支上。
另外,Git还提供了切换分支的功能,可以在不同的分支之间自由切换。这意味着可以根据需要快速切换到不同的分支,查看或编辑特定的代码。
分支归根到底是git内的操作,工作目录是怎么样的呢? 当切换到一个新分支时,Git会根据该分支的最后一次提交更新工作目录。这意味着工作目录中的文件和目录会被替换为该分支的最新版本。如果在切换分支之前对工作目录进行了修改,那些修改可能会被保存下来,但在切换到新分支时,它们可能与新分支的代码产生冲突,需要进一步处理。 需要注意的是,未提交的修改不会随着分支的切换而消失。即使切换分支,那些修改仍然存在于工作目录中,只是这些修改可能与当前分支的代码出现冲突。在切换分支之前,可以使用
git stash
命令将这些修改暂存起来,以便稍后在相关分支上继续工作。 所以在本地操作的时候,切换分支的时候,工作目录中的内容也会切换;
标签就是给定版本的符号名称。它永远都指向相同对象,并且不会变更。标签的用途是,对于所有开发人员来说,都可以使用符号名称引用给定的修订,而且该符号对所有开发人员的意义都是一致的。
在Git中,标签(Tag)是用于给特定提交(commit)打上一个有意义的、永久性的标记。标签相当于一个固定指向某个特定提交的引用,通常用来表示项目的版本、发布或者重要的里程碑。
标签可以用来表示项目的版本号。当代码开发到一个稳定状态并准备发布时,我们可以给这个版本打上一个标签,方便其他人获取并确保他们拿到的是同一个版本的代码。
其次,标签还可以用来管理发布过程。每次发布新版本时,我们可以为这个版本创建一个标签。这样,我们可以方便地回溯、查看和获取这个特定版本的代码,并且同时也能追踪已发布版本的变化和修复。
另外,标签还可以用来标记项目开发过程中的重要里程碑,如测试阶段、功能完成、重要修复等。我们可以给这些重要节点打上标签,以后可以根据标签来查找相关的提交。
Git
有commit
,为什么还要引入tag
? “请把上周一的那个版本打包发布,commit
号是6a5819e…
” “一串乱七八糟的数字不好找!” 如果换一个办法: “请把上周一的那个版本打包发布,版本号是v1.2
” “好的,按照tag v1.2
查找commit
就行!” 所以,tag
就是一个让人容易记住的有意义的名字,它跟某个commit
绑在一起。
上面的项目是一个空的项目,里面一个文件都没有,所以先从零开始;
使用touch readme.md
命令新增一个readme的MarkDown文件,这个项目就不是空的了;
将要上传的文件添加到Git的暂存区,使用以下命令:
git add filename // 添加单个文件
git add . // 添加所有文件(包括新的和修改过的)
例如将我们刚才创建的readme.md
上传到暂存区,没有报错就是上传成功了;
我们再新建两个文件,然后上传所有文件,如下,没有报错就成功了;
将暂存区中的更改提交到代码库,使用以下命令:
git commit -m "Commit message" // 提交并添加提交信息
-m
后面输入的是本次提交的说明,一般用来记录改动记录,这个说明是非常必要的,个人的项目方便回退查看,团队项目方便阅读;
上传结果如下,提交成功后,git会有提示,在这次提交中,共有3个文件被更改,但没有插入或删除任何内容。
查看提交历史:使用git log
命令可以查看提交历史,包括每个提交的哈希值、作者、提交日期和提交消息等信息。默认以最新的提交开始显示,按照时间倒序排列。
git log
查看文件变更:使用git diff
命令可以比较当前工作目录中的文件与最新提交之间的差异。它可以显示插入的内容、删除的内容以及修改的内容等信息。
git diff
查看文件状态:使用git status
命令可以查看工作目录中文件的状态,包括已修改、已暂存、未跟踪等状态。它会列出所有变更的文件以及它们所处的状态。
git status
查看特定提交的内容:使用git show
命令可以查看某个特定提交的详细信息,包括提交的更改内容和元数据。需要提供该提交的哈希值或其他引用(如分支名)。
git show commit_hash
以上是一些常用的Git命令,用于查看版本库中的内容。通过这些命令,您可以了解提交历史、文件变更以及当前文件的状态,进而进行版本控制和代码调试等操作。
上面的操作,相当于是完成了第一版的提交,接着进行文档修改后上传,查看相关的一些变化。
上面初始的版本中,包含三个文件,分别是readme.md、test.py、test2.py
;
向test.py
中写入print("Hello world!")
;
向test2.py
中写入print("Hello test2!")
;
这里写入的方式有很多,建议是使用安装的时候的
vim
就行,也可以通过其他编辑器编辑也行,这无所谓;
git diff
查看工作区的文件变更如下图,运行命令后输出了相关提示;
在输出中的警告表示,在下次Git操作时,LF(Line Feed,换行符)将被CRLF(Carriage Return Line Feed,回车换行符)所取代。这通常发生在Windows环境下,因为Git在Windows上默认使用CRLF作为换行符,而不是Unix风格的LF。这个警告是提醒你关于换行符的差异,但不会影响实际的差异显示和文件修改。
接下来是具体的差异内容,使用---
表示原有文件的位置,+++
表示修改后的文件的位置。在每个文件的差异后面,使用@@ -x,y +z,w @@
格式的行表示差异的位置信息。其中,x,y
表示原有文件中被修改部分的起始行和结束行,z,w
表示修改后的文件中对应的起始行和结束行。
也提示test.py文件添加了一行代码print("Hello world!")
,而test2.py文件也添加了一行代码print("Hello test2!")
。
git status
查看文件状态逐行解释:
在main分支中
Changes to be committed
:这一部分列出了即将被提交的修改。在这里,test2.py
文件被修改并已经添加到了暂存区。 可以使用git restore --staged <file>...
命令来取消对文件的暂存操作,将其移出暂存区。modified
指示被修改还未提交的文件;Changes not staged for commit
:这一部分列出了未暂存的修改。在这里,test.py
文件被修改但没有被添加到暂存区。 可以使用git add <file>...
命令将文件添加到暂存区,以将其包含在下一次的提交中。
再修改一下readme.md
,并查看多个文件的时候的状态;
修改未暂存:
修改并暂存:
git log
查看版本库内的上传日志可以看到提交了两次,以及每次提交的时候的基本信息;
git show
查看第二次上传的详细信息就可以看到本次上传的主要信息了;
命令版本号没必要写全,前几位就可以了,Git会自动去找。当然也不能只写前一两位,因为Git可能会找到多个版本号,就无法确定是哪一个了。
这里就可以看到第三次提交的信息,首先是test.py新增了一行代码,其次是test2.py中代码发生了变化;
以上就是git版本更新的基本操作和信息查看;
为什么reset
和checkout
要单独拿出来说,是因为版本回退在git中涉及版本回退有两个常见的操作,当涉及到回退版本或切换分支时,git reset
和git checkout
是两个常用的Git命令,并且有一些区别。
git reset
命令:
git reset
用于移动HEAD指针和当前分支引用来更改提交历史。
git reset
会修改提交历史,因此在公共仓库中使用时需要小心。它可以撤销提交、删除提交或重写提交历史。
git reset
根据指定的参数选项(如--mixed
、--soft
和--hard
)来决定是否更改索引和工作目录。
--soft
:仅移动HEAD指针和当前分支引用,不更改索引和工作目录。这允许你撤销最近的提交并重新提交。--mixed
(默认选项):移动HEAD指针和当前分支引用,并将索引重置为指定的提交。但是,不更改工作目录。这样可以撤销提交并保留更改的副本供进一步修改。--hard
:彻底移动HEAD指针、当前分支引用和索引,并重置工作目录为指定的提交。这将丢弃所有未提交的更改。git checkout
命令:
git checkout
用于切换分支、还原文件或查看历史版本。git checkout
不会更改提交历史。它主要用于浏览和查看已经存在的提交。git checkout
可以通过指定分支或提交标识符,切换到不同的分支或恢复特定版本的文件。它会将HEAD指针和当前分支引用移动到新的目标。简而言之,git reset
主要用于修改提交历史,并具有对索引和工作目录的不同影响。而git checkout
主要用于切换分支、还原文件和查看历史版本,不会修改提交历史。
我们先看看checkout的版本回退操作,至于切换分支等操作,后面再讲,这里只将回退;
为了理解,我们重新创建一个项目,只有一个test.py
文件;
第一版
空
第二版
print("2.0")
第三版
print("3.0")
现在我们觉得第三次提交的内容中test.py修改的内容不对,我们要回到第二版,在第二版的基础上调整;使用git checkout <commit_id>
就可以实现回退了
如上,就已经完成的切换,Git发出提示: 切换回去之后,就开始没有关联任何分支了,相当于是把那个版本拿出来独立在分支之外了; 也就是说,
checkout
会切换到旧版本,切换回去之后可以查看旧版本的状态,但是他并不能改变提交历史,也就是不管你怎么操作,都不会改变当前分支的提交记录和版本; 如果要保留checkout
之后的修改,可以创建一个新的分支;
print("2.0——>4.0")
发现已经成功了,但是是在第二版上叠加了一个版本,并不是在第三版的基础上叠加了版本,这就印证了前面说的不会修改分支的提交历史;
这个时候有个报错,说切换回main分支的时候,有一个提交不属于任何分支,可以选择创建一个新的分支来保留这个提交。然后可以切换到新的分支上进行开发或修改。
这里就可以看到,
main
分支的提交历史并没有发生任何变化; 那么如何将那个孤立的提交给放到main
分支里面做第四版呢? 其实是不能够直接做到的,那你会问这样的checkout
有什么意义,当然有,只是流程不能是切换到旧版本,然后修改提交,然后将孤立的那个提交直接拿到旧分支中;两个方案:
git
的提示那样,创建一个新的分支,然后将新分支合并到旧分支中(具体操作在后面的分支去记录);checkout
回旧版本后,修改了不要提交,而是将修改暂存,然后切换回旧分支,拉回修改进行合并;首先切换到第二版本的分支,然后修改文件,注意这里是重新回到第二版,然后重新修改代码;
上面的修改和提交依旧还存在;
也就是我们最开始切换到第二个版本,修改代码提交的那个‘第四版’;现在不属于任何分支,也称作游离提交; 游离提交无法通过常规的 Git 命令进行删除,提交历史是 Git 存储的一部分,游离提交会在一段时间后被 Git 的垃圾回收机制清理掉。
接着通过git stash save "Your stash message"
保存修改到临时区:
切换回主分支:
查看暂存区内容:
将暂存区的内容应用到当前分支:
这里就开始提示在合并时遇到冲突,由于两个地方都有修改,但是git不知道保留哪个,所以报错,可以看到现在文件里面的内容如下:
需要自行进行编辑选择;这里我们不选择,直接上传,提交;
如上,我们就完成了一个版本的切换;
但是我们发现,这个暂存还在:
可以通过git stash drop <stash_id>
删除:
这样就完成了删除,或者将上面的git stash apply
换成git stash pop
;git会在应用暂存的时候同时删除那个暂存;
上面,我们的版本库中已经有四个版本了;可以通过git log
可以直接查看(这里博主换了个环境重新搭的,所以hash值和上文不一样,注意区分噢~):
用于回退 Git 提交的通常包含三个命令,它们之间的区别在于对暂存区和工作目录的处理方式不同。
git reset --soft
: git reset --mixed
: git reset
命令相同。git reset --hard
: 总结:
git reset --soft
:保留修改和暂存区的文件,可重新提交。git reset --mixed
:保留修改但取消暂存,需要重新添加和提交文件。git reset --hard
:彻底丢弃当前提交及之后的修改,无法恢复。为了区分工作区、暂存区、git提交历史;首先修改一下最新的文件,然后添加到暂存区,接着再修改一下文件;
在这里,本来是
print("2.0-->4.0")
; 暂存区的内容是print("3.0-->4.0")
;
工作区的内容是print("4.0")
;
使用git reset
回退,上一个版本就是HEAD^
,上上一个版本就是HEAD^^
,当然往上100个版本写100个^
比较容易数不过来,所以写成HEAD~100
;
当然也可以使用提交的哈希值来定位某次提交;
运行上面命令,就可以完成回退了,查看提交日志,发现第四次提交已经不再了;
然后分别查看暂存区和工作目录的文件内容;
暂存区如下,可以发现和回退前一致:
工作目录的内容也是和回退前一致的操作;
后悔了怎么办?
后悔了也就太简单了,还是使用git reset --soft
;
但是不能用HEAD了,要找到对应的那个提交的哈希值,在这个案例中就是第四次提交的哈希值:
查看提交的版本中内容、暂存区内容、工作区内容:
版本中和还原前一致
暂存区和还原前一致:
工作区和还原前一致:
同样使用HEAD^
的方式回退,回退成功后给出提示:
表示 test.py
文件有未暂存的更改。由于使用了 --mixed
参数,保留工作区修改但取消暂存。
查看本版本内容,是对应第三版的内容:
暂存区的内容空了:
工作区的内容没变:
这里后悔了的话,是不能完全回去的哈,就是暂存区的内容已经删除了,再回去的话,暂存区的内容也没了; (如果有办法的话,欢迎纠正哈)
在此之前,我们还是将工作区、暂存区的内容调整到最初的一样哈;
然后使用使用HEAD^
的方式回退,命令:git reset --hard HEAD^
;
查看版本中内容,内容回到了第三版的内容:
暂存区内容为空:
工作区内容为空:
这里后悔了,要回到第四版的话,也是很简单的,直接使用命令:
git reset --hard a5b4
即可; 同样,回到第四版,也不能恢复暂存区和工作区的内容。
不仅仅只有上述三种形式的 git reset
命令,还有其他一些变种形式。
除了 git reset --soft
, git reset --mixed
和 git reset --hard
,还有其他的 git reset
变种命令:
git reset HEAD <file>
:
<file>
参数代表要取消暂存的文件名。如下,可以将指定的文件从暂存区恢复到工作区。
git reset <commit>
:
<commit>
可以是提交的哈希值、分支名或标签名。这个其实和git reset --mixed是一样的;
git reset --keep <commit>
:
<commit>
,这样就撤销了 <commit>
以及之后的所有提交。reset
模式,--keep
选项会保留工作目录中的所有修改。这意味着未添加到索引的更改不会丢失。<commit>
不一致的部分,那么这些更改将会被保留,但会被标记为未暂存的更改。使用分支的好处是可以保持代码库的整洁同时允许并行开发。每个人可以在自己的分支上工作,不会影响到其他人。当一个功能或修复完成后,可以将分支合并回主分支(通常是 master
分支),从而将更改整合到项目中。
默认分支:master
在 Git 中,默认创建的分支通常被称为 master
或 main
分支。这是代码库的主要分支,包含了最新可用的稳定代码。
创建新分支
要创建新的分支,可以使用以下命令:
git branch <branch_name>
这将在当前提交上创建一个名为 <branch_name>
的新分支,但还没有切换到该分支。
如下,没有报错即新建成功!
切换分支
要切换到已存在的分支,可以使用以下命令:
git checkout <branch_name>
这将会将工作目录和代码库切换到名为 <branch_name>
的分支上。
创建并切换分支
git checkout
命令加上-b
参数表示创建并切换:
Git 2.23 版本之后,可以使用以下命令来快速创建并切换到新分支:
git switch -c <branch_name>
这将创建一个名为 <branch_name>
的新分支,并将工作目录和代码库切换到该分支上。
查看分支
要查看所有本地分支,可以运行以下命令:
git branch
当前分支前面会有一个星号 *
。另外,可以添加 -r
选项来查看远程仓库的分支。
提交版本
修改一下文件内容,将里面的内容修改为5.0并提交,都是同样的操作:
合并分支
当在一个分支上工作完成后,通常需要将其合并回主分支或其他目标分支。要合并分支,可以使用以下命令:
git merge <branch_name>
这将把名为 <branch_name>
的分支合并到当前所在的分支(通常是 master
分支)。
如下,先切换回主分支,然后将分支branch1
合并到当前分支,然后查看提交历史:
删除分支
当分支的任务完成后,可以删除不再需要的分支。要删除分支,可以使用以下命令:
git branch -d <branch_name>
这将删除名为 <branch_name>
的分支。如果分支上还有未合并的更改,需要使用 -D
参数来强制删除。
switch命令
Git 2.23 版本引入了 git switch
命令,用于切换分支和创建新分支。git switch
命令的功能与之前的 git checkout
命令有所重叠,但是更加直观和易于使用。
1. 切换到已存在的分支
要切换到已存在的分支,可以使用以下命令:
git switch <branch_name>
这将使当前工作目录切换到名为 <branch_name>
的分支。
2. 创建并切换到新分支
要创建一个新分支并立即切换到该分支,可以使用以下命令:
git switch -c <new_branch_name>
这将创建一个名为 <new_branch_name>
的新分支,并将当前工作目录切换到该分支。
3. 切换到远程分支
对于一个远程分支,你可能需要先将其拉取到本地,然后再切换到该分支。可以使用以下命令完成这个过程:
git switch --track <remote_branch_name>
这将拉取名为 <remote_branch_name>
的远程分支并创建一个与其关联的本地分支,并将当前工作目录切换到该分支。
4. 强制切换分支
如果在切换分支时存在未提交的更改,Git 默认情况下会阻止你切换分支。然而,有时你可能希望强制切换分支并放弃未提交的更改。可以使用以下命令:
git switch -f <branch_name>
这将强制将当前工作目录切换到名为 <branch_name>
的分支,并丢弃未提交的更改。
git switch
和git checkout
是在 Git 中用于切换分支的两个命令,它们有一些区别。以下是它们之间的主要区别:
git switch
的操作方式更加直观和一致。它专门用于切换分支和创建新分支,更符合用户的直觉。而 git checkout
则具有更多的功能,可以用于切换分支、创建新分支、恢复文件等。git checkout
可能会导致未提交的更改被覆盖或丢失。例如,在切换分支之前,如果有对当前分支已修改但尚未提交的文件进行更改,那么 git checkout
会直接将这些更改应用到目标分支。这可能会导致不可预料的结果。相比之下,git switch
不会自动应用未提交的更改,它会提醒你先处理这些更改,然后再切换分支。git switch
的命令参数和选项更加语义化和直观。例如,使用 -c
选项来创建并切换到一个新分支,使用 --detach
选项来切换到一个游离的 HEAD(不指向任何分支)。这使得分支操作更加易于理解和记忆。git switch
是在 Git 2.23 版本中引入的新命令,而 git checkout
是 Git 的旧命令。随着时间的推移,Git 社区更倾向于使用和推荐 git switch
命令,因为它更直观、功能单一,并且在处理未提交的更改时更加安全。 需要注意的是,虽然 git switch
更加推荐使用,但在早期版本的 Git 中仍然可以使用 git checkout
命令,并且它仍然是有效的。对于一些高级或特殊的用例,git checkout
可能提供更多灵活性和功能。
总的来说,git switch
是一个更简洁、直观并且推荐使用的命令,专门用于分支切换和创建新分支。而 git checkout
则是一个更通用、功能更多的命令,可以用于更多其他场景,如恢复文件、创建或删除分支等。
添加标签
切换到对应的分支,使用命令:git tag tagname
为最新的提交打标签:
使用命令git tag
查看所有标签:
为历史提交打标签
之前某次提交忘记打标签了,为其打标签:
首先查看历史提交,git log --pretty=oneline --abbrev-commit
,该命令的作用是以单行的形式显示提交历史,并使用缩略的提交哈希值。
为第一版打标签:
用git show <tagname>
查看标签信息:
删除标签
使用git tag -d tagname
即可完成标签的删除;
远程仓库有很多,流行的主要就有github、gitee等,这里使用gitee来演示,创建账号和新建仓库具体操作就不演示了;
这里新建一个test_gitee的远程仓库;
git remote add
命令,并将 <remote_name>
替换为想要的远程仓库名称,<remote_url>
替换为远程仓库的 URL。使用git remote -v
查看远程仓库详细信息:
这里是可以添加多个远程仓库的噢
git push
命令将本地仓库中的分支推送到远程仓库。指定要推送的分支,以及远程仓库的名称和分支。例如,以下命令将本地 main
分支推送到名为 origin
的远程仓库。Copy Codegit push <remote_name> <branch_name>
如果是首次推送分支,可能需要使用 -u
参数来设置跟踪。例如:
Copy Codegit push -u <remote_name> <branch_name>
如下,便完成了推送:
Enumerating objects: 12, done.
:Git 正在遍历要推送的对象。Counting objects: 100% (12/12), done.
:Git 统计了要推送的对象数量。Delta compression using up to 16 threads
:Git 使用了多线程进行增量压缩。Compressing objects: 100% (4/4), done.
:Git 完成了对象的压缩。Writing objects: 100% (12/12), 947 bytes | 947.00 KiB/s, done.
:Git 将对象写入远程仓库。Total 12 (delta 0), reused 0 (delta 0), pack-reused 0
:Git 显示了推送的总体情况,此次推送没有增量数据(delta)。remote: Powered by GITEE.COM [GNK-6.4]
:远程仓库的信息,显示你正在使用 Gitee 平台。To https://gitee.com/zishu-yanluo/test_gitee.git
:推送的目标远程仓库 URL。[new branch] master -> master
:远程仓库中创建了一个新分支 master
,与本地的 master
分支关联。branch 'master' set up to track 'test_gitee/master'.
:本地的 master
分支已配置跟踪远程仓库的 test_gitee/master
分支。在远程仓库中也可以查看到我们的提交了:
从远程仓库中获取最新的代码更新是很重要的,就像从云盘上下载最新的文件到你的电脑一样。要拉取远程仓库的更新,需要执git pull
操作:
git pull
命令的一般语法为:
git pull <远程仓库名> <远程分支名>
具体解释如下:
<远程仓库名>
:指定要获取更新的远程仓库,通常是使用 origin
来表示默认远程仓库。<远程分支名>
:指定要获取更新的远程分支。git pull
命令的执行过程大致如下:
git fetch
命令,从指定的远程仓库中获取最新的提交,但不会应用到本地分支。git merge
命令,将获取的提交与当前分支进行合并。在执行 git pull
命令时,可能会遇到以下情况:
git pull
会自动合并远程分支的更新到当前分支,并创建一个新的合并提交。git pull
默认会尝试自动合并。如果合并过程中发生冲突,你需要手动解决冲突后再提交。git pull
,可以使用 git pull --force
命令。另外,还有一些 git pull
命令的选项可以进一步控制其行为,例如:
--rebase
:使用 rebase 而不是 merge 来合并远程分支的更新。--no-commit
:获取远程更新后不自动创建新的合并提交。--ff-only
:仅在快进合并的情况下才执行合并操作,否则终止。如下,现在远程仓库的版本是第四次提交:
现在新建一个分支并回退到第三版:
运行git pull
命令没报错即拉取成功:
在使用 git clone
命令进行克隆时,你有两种选择:
克隆到新建的项目目录:你可以指定一个新的项目目录,在该目录下执行 git clone
命令来克隆远程仓库。这将在指定的目录中创建一个新的项目,并将远程仓库的内容复制到该目录中。
例如:
git clone <远程仓库地址> <新项目目录>
在这种情况下,git clone
命令会自动创建一个与远程仓库同名的项目目录,并将远程仓库的内容复制到该目录中。
克隆到已存在的项目目录:如果你想将远程仓库的内容复制到一个已存在的项目目录中,可以直接进入该目录,并执行 git clone
命令。这将在当前目录中创建一个新的分支,并将远程仓库的内容复制到该分支中。
例如:
cd <已存在的项目目录>
git clone <远程仓库地址>
在这种情况下,git clone
命令会将远程仓库的内容复制到当前目录中,并自动创建一个新的默认分支。
注意:
默认情况下,
git clone
命令会克隆远程仓库的所有分支。但是,克隆下来的分支在本地仓库中会以远程分支的形式存在,并不会自动创建与每个远程分支对应的本地分支。 你可以使用git branch -r
命令查看克隆下来的所有远程分支,使用git branch -a
命令查看所有本地分支和远程分支。
要将远程分支创建为本地分支,可以使用以下命令:
git checkout -b <本地分支名> <远程仓库名/远程分支名>
这将创建一个新的本地分支,并将其设置为指定远程分支的跟踪分支。
另外,如果你只想克隆特定的分支而不是所有分支,可以使用 --single-branch
选项。例如:
git clone --single-branch -b <分支名> <远程仓库地址>
这样只会克隆指定的分支,并忽略其他分支。
分支
创建远程分支并推送:要在本地创建一个新分支,并将其推送到远程仓库,可以使用以下命令:
git checkout -b <branch-name>
git push origin <branch-name>
这将创建一个名为<branch-name>
的新分支,并将其推送到名为origin
的远程仓库。
删除远程分支:要删除远程仓库中的分支,可以使用以下命令:
git push origin --delete <branch-name>
这将从远程仓库中删除名为<branch-name>
的分支。请确保你有足够的权限来执行该操作。
查看远程分支:要查看远程仓库中的分支,可以使用以下命令:
git branch -r
这将显示远程仓库中的所有分支。
拉取远程分支:要将远程仓库的特定分支拉取到本地仓库,可以使用以下命令:
git checkout -t origin/<branch-name>
这将创建一个与远程仓库中的<branch-name>
分支相对应的本地分支,并将其切换到该分支。
标签
创建的标签都只存储在本地,不会自动推送到远程。
需要使用git push origin <tag-name>
命令显式地将标签推送到远程仓库。
或者推送全部标签:git push origin --tags
可以使用git tag -d <tag-name>
命令删除本地的标签。类似地,通过git push origin :refs/tags/<tag-name>
命令可以从远程仓库删除标签。
具体用法如下:
<tag-name>
表示你要删除的标签的名称。origin
是远程仓库的名称,通常指向你的远程仓库URL。 举个例子,如果你想删除名为v1.0
的标签,可以执行以下命令:
Copy Codegit push origin :refs/tags/v1.0
执行命令后,Git会将该命令推送到远程仓库,远程仓库会删除对应的标签。
需要注意的是,这个命令只会删除远程仓库中的标签,而不会影响本地仓库中的标签。
如果两个人的本地仓库都有一个同样的分支,并且同时推送到远程仓库,会导致冲突的发生。这是因为远程仓库不能直接处理两个相互冲突的提交。 具体情况如下:
在这种情况下,解决冲突的方法如下:
git pull
命令。git pull
命令会合并远程分支的更改到本地分支,并且可能触发冲突。git add
命令将修改的文件标记为已解决冲突。git commit
命令提交解决冲突后的更改。此时,会生成一个新的合并提交。总之,如果两个人的本地仓库都有相同的分支,并且同时推送到远程仓库,会导致冲突的发生。在这种情况下,需要先拉取最新的远程更新,解决冲突后再推送修改到远程仓库。这样可以确保所有人的更改都能够合并,并保持代码的一致性。