概要
本文介绍在 Mac 环境下使用 Git 版本控制的基础概念与操作流程,帮助开发者理解 Git 的核心机制。
整体架构流程
Git 包含四个核心概念:工作区、缓存区、本地仓库和远程仓库。本文以 PyCharm 为例,说明如何在 IDE 中搭建项目并与 GitHub 交互。
1. 工作区
工作区即项目本身的路径。每个项目在 PyCharm 中拥有独立的路径和文件夹,所有文件保存在该项目子目录下。

创建项目后,在项目终端查看根路径。此时尚未初始化 Git 仓库,无法执行 Git 命令。确保已安装 Git(Mac 用户可使用 Homebrew 安装),在项目内执行 git init 初始化仓库。

成功创建空 Git 仓库后,即可开始执行 Git 命令。
2. 缓存区
缓存区是 Git 特有的中间区域。在工作区创建或修改文件后,Git 能识别改动,但文件处于未追踪(untracked)状态。使用 git status 可查看当前仓库状态及文件变动。

新建文件(如 f1.txt)后,Git 识别为未追踪。使用 git add <file_name> 将文件添加至缓存区,批量添加可使用 git add .。

文件加入缓存区后等待提交。若对 f1.txt 进行编辑,再次运行 git status,Git 会提示工作区与缓存区内容不一致,显示更改(change)但未报备。
日常开发中,建议仅在最终版本确定时将其加入缓存区,无需频繁同步工作区与缓存区的每一个修改版本。
3. 提交至 Git 本地仓库
缓存区中的内容标记为'待提交'(staged)。满意后将文件提交至本地仓库,使用 git commit -m '提交说明'。

提交后查看日志,显示变更统计(如 2 files changed, 21 insertions(+))。若后续删除内容,则显示 deletion (-)。

继上次提交后再次修改 f1.txt 并删除一行,提交说明为 'edit second time for f1 delete 1 row',Git 更新提交记录。
针对提交记录的查看和其他命令
使用 git config --list 查看配置参数。常用且需手动修改的参数包括用户名和用户邮箱,邮箱需与远程仓库(如 GitHub)注册邮箱一致。
# 配置用户名和邮箱
git config --global user.email "<email>"
git config --global user.name "<name>"
# 清除配置
git config --global --unset-all user.email
git config --global --unset-all user.name
# 初始化默认分支设为 main
git config --global init.defaultBranch main
# 配置代理 IP
git config --global http.proxy "<ip>"
git config --global https.proxy "<ip>"
# 查看所有配置参数 (q 退出)
git config --list
# 查看日志提交记录 (q 退出)
git log
git log 可查看所有提交记录,包括 Hash ID、时间及备注,按时间倒序排列。
若误操作提交了错误版本,可使用以下命令调整:
# 撤回某次提交,新增反向回溯提交
git revert <hash id> --no-edit
# 强制返回某次提交状态,抹除该提交后的所有记录和版本数据
git reset --hard <hash id>
例如对 f2 文件进行了三次操作(创建、修改 1、修改 2),若想保留第二次修改而撤回第一次,可使用 revert。但因上下文依赖,Git 可能不允许直接跳过中间版本。此时只能使用 reset 强制回退。
git reset --hard 非常危险,会删除工作区数据。若仅希望退回仓库版本,可考虑:
# 假设最新版本 v5 -> 回退至 v3
# 默认 mixed reset 回退版本
git reset <hash id>
# 效果:
# 1. git 仓库 log 头指向指定提交 id v3
# 2. 缓存区清空,仅保留 v3 的版本
# 3. 但工作区的修改 v5 版本保留!
# 4. 运行 git status 显示"未暂存的修改",当前 v5 修改未和缓存区同步
# 5. 如果想重新保存 v5 需要再次 git commit -m '保存最新 v5' file v5
# soft reset 软回退版本
git reset --soft <hash id>
# 效果:
# 1. git 仓库 log 头指向指定提交 id v3
# 2. 暂存区 v5 版本保留(之前的 v5 版本变成已暂存状态)
# 3. 工作区也保留 v5
# 4. 运行 git status 显示"要提交的变更",当前 v5 修改已加入缓存区但未提交
# 5. 此时可以在工作区将 v5 修改至满意,然后 git commit -m 'new v5' file v5 替换缓存区里之前保留的 v5 并提交
本地仓库与远程 GitHub 仓库连接
本地存储相当于硬盘,GitHub 相当于云端。文件同步至云端后,可随时拉取。

绑定远程仓库命令:
# 根据 url 绑定远程仓库
git remote add origin <Repo Url>
# 命名当前本地仓库主分支为 main 以便和 GitHub 平台同步
git branch -M main
# 推送&绑定 本地仓库 main 分支内容 与 远程仓库
git push -u origin main

查看远程仓库命名(默认 'origin')和 URL。

使用 git log 查看提交操作后,尝试将本地仓库内容提交至远程仓库。


提交成功,本地 repo 文件已同步至 GitHub。
主支 & 分支合并
场景:创建项目并初始化,创建 main 主支,add 并 commit 三次(a->b->c)。新创建分支 01,checkout 至 01,add 并 commit 两次(d->e)。想合并 01 到 main,形成线性历史 a->b->c->d->e。
原始状态:
# a---b---c main
# \
# d---e 01

切换至分支 01 执行变基合并:
使用变基(Rebase)来实现线性历史
# 切换至 01 分支
git checkout 01
# 将 01 分支变基到 main 分支上
git rebase main
# 此操作把 d 和 e"移动"到 c 之后
# a---b---c---d'---e' 01 (main)
# 执行时发生了什么:
# 1. Git 找到 01 分支和 main 分支的共同祖先(c)
# 2. 临时保存 01 分支的更改(d 和 e)
# 3. 将 01 分支指针移到 main 的最新提交(c)
# 4. 重新应用保存的更改(d 和 e)
执行完毕后切换回 main 主支查看日志,发现没有合并记录。

在 main 主支上使用快进合并:
# 切换到 main 分支
git checkout main
# 使用快进合并(因为现在 main 是 01 的祖先)
git merge 01

合并完成后再次查看日志,01 分支的操作已并入 main。完成合并后同步新内容至 GitHub 仓库。

同步成功。

