lab0
思考题
Thinking 0.1
-
在前述已初始化的
~/learnGit
目录下,创建一个名为README.txt
的文件。执 行命令git status > Untracked.txt
(其中的 > 为输出重定向,我们将在 0.6.3 中 详细介绍)。 -
在
README.txt
文件中添加任意文件内容,然后使用add
命令,再执行命令git status > Stage.txt
。 -
提交
README.txt
,并在提交说明里写入自己的学号 -
执行命令
cat Untracked.txt
和cat Stage.txt
,对比两次运行的结果,体会README.txt
两次所处位置的不同。不一样。第一次是在工作区添加了文件,没有提交的暂存区。而第二次提交到了暂存区,只是没有commit到HEAD。而由于都没有进行commit ,因此都没有跟踪,于是提示是为跟踪的文件。
Thinking 0.2
-
仔细看看0.10,思考一下箭头中的 add the file 、 stage the file 和commit 分别对应的是 Git 里的哪些命令呢?
add the file : 对应
git add
stage the file : 对应
git commit
commit : 对应
git checkout
Thinking 0.3
-
代码文件 print.c 被错误删除时,应当使用什么命令将其恢复?
使用
git restore print.c
即可 -
代码文件 print.c 被错误删除后,执行了 git rm print.c 命令,此时应当使用什么命令将其恢复?
git restore --staged print.c git restore print.c
-
无关文件 hello.txt 已经被添加到暂存区时,如何在不删除此文件的前提下将其移出暂存区?
使用
git restore --staged hello.txt
即可
Thinking 0.4
-
找到在 /home/22xxxxxx/learnGit 下刚刚创建的 README.txt 文件,若不存在则新建该文件
-
在文件里加入 Testing 1, git add, git commit,提交说明记为 1。
-
模仿上述做法,把 1 分别改为 2 和 3,再提交两次。
-
使用 git log 命令查看提交日志,看是否已经有三次提交,记下提交说明为3 的哈希值
进行操作后可以看到确实有了三次提交的记录
-
进行版本回退。执行命令 git reset --hard HEAD^ 后,再执行 git log,观察其变化
此时git log的第一项是2,相当于撤销了第三次提交
-
找到提交说明为 1 的哈希值,执行命令 git reset --hard
后,再执行 git log,观察其变化。 强制撤销到1时候的版本,因此git log只能看到1的提交记录
-
现在已经回到了旧版本,为了再次回到新版本,执行 git reset --hard
,再执行 git log,观察其变化。 可以看到又恢复了原样,也就是回到了新版
Thinking 0.5
-
执行如下命令,并查看结果
- echo first
- echo second > output.txt
- echo third > output.txt
- echo forth >> output.txt
>
是覆盖写入>>
是追加指令
Thinking 0.6
-
使用你知道的方法(包括重定向)创建下图内容的文件(文件命名为 test),将创建该文件的命令序列保存在 command 文件中,并将 test 文件作为批处理文件运行,将运行结果输出至 result 文件中。给出 command 文件和 result 文件的内容,并对最后的结果进行解释说明(可以从 test 文件的内容入手) . 具体实现的过程中思考下列问题: echo echo Shell Start 与 echo
echo Shell Start
效果是否有区别; echo echo $c>file1与 echoecho $c>file1
效果是否有区别前两条指令的效果是有区别的,而后两条指令的效果是没有区别
加上反引号相当于将反引号的内容重定向作为参数
因此
echo Shell Start # 标准输出为Shell Start echo `echo Shell Start` # 后面指令的标准输出为Shell Start ,作为echo的参数,因此输出还是Shell Start
而
c=3 echo echo $c>file1 # 相当于是echo指令输出了echo $c,其中$c 为 3,然后重定向到文件中 echo `echo $c>file1`# 相当于是首先`echo $c>file1` ,将$c的值重定向到了file1中,标准输出为空,将标准输出作为前面的echo的参数,因此输出为空,但是echo会默认添加一个换行符,因此还有一个换行
难点分析
CLI
第一个难点在于如果之前习惯了使用
GUI
界面,刚开始接触这种命令行界面是不够熟悉的。依稀记得自己第一次接触
ubuntu
时探索了好久好久,当时使用的还是图形化界面。
命令行界面(CLI)是基于文本的界面,可以在其中输入与计算机操作系统交互的命令。CLI在默认Shell的帮助下运行,该Shell位于操作系统和用户之间。
Shell负责处理各种任务,例如命令解析、环境管理和流程执行等。
此外还可以自定义Shell环境。为此,可以设置环境变量、定义别名(较长命令的快捷方式等)以及为自动化或重复任务创建Shell脚本。
- 命令的工作原理
在CLI中输入命令是,系统会执行以下步骤:
- Shell命令行解释器解析输入的命令以了解其结构,并且分离命令名称、选项和参数
- Shell在其可用命令列表中查找命令名称。命令名称代表用户希望操作系统执行的操作
- Shell搜索系统的PATH变量(系统文件所在的目录列表),以查找与该命令关联的相应文件
- CLI Shell会调用相应的文件,并且传递任何指定的选项和参数作为输入。
- 操作系统执行所需的操作
- 此操作可能会生成输出,例如信息性消息、错误消息、请求的数据或操作结果
- CLI Shell会显示输出,因此可以看到命令的结果
CLI Shell循环运行,等待输入另一条指令。
Linux
Linux与Windows命令行的一些指令的差异可能会让人感到措手不及。比如bash
的指令和powershell
以及cmd
的指令是有比较大的差异的可能让人感到不熟悉。
同时也不熟练的使用Linux的一些基本操作。包括sudo
等
Vim
由于使用CLI
的缘故,我们没有很好的图形化文本编辑器,于是需要使用Vim
或者emacs
等文本编辑工具。
对于Vim的快捷键以及工作模式不熟悉会带来比较大的难点。
对此我强烈推荐跟着
vimtutor
走一遍,基本上可以熟悉大多数的操作,以及基本的几个vim模式
其实简单的用法也只有
- 输入
i
进入编辑模式 - 点击
Esa
退出编辑模式 - 输入
:w
保存,:wq
保存并退出
基本上可以完成最基本的使用,甚至上下左右可以直接使用箭头键,都不需要使用到hjkl
。
GCC
对于gcc
的基本使用指令不够了解。
tldr
是个非常好用的命令用法查询工具,狠狠种草
可以看到gcc
的基本用法
gcc
是一个C语言编译器g++
是一个C++语言编译器
语法:gcc [选项]... [文件]...
选项:
-c 仅编译,不链接
-o 指定输出文件
-E 预处理
-S 汇编
-l 指定库文件
-L 指定库文件路径
-I Path/to/head/file 指定头文件路径
-D 定义宏
-wall 显示所有警告
-g 生成调试信息
-std=c99 指定C语言标准
参数:
file.c 源文件
示例
gcc -o hello_world hello_world.c #编译hello_world.c文件为hello_world可执行文件
gcc -c hello_world.c #编译hello_world.c文件为hello_world.o目标文件
gcc -E hello_world.c #预处理hello_world.c文件
gcc -S hello_world.c #汇编hello_world.c文件
gcc -o hello_world hello_world.c -lm #编译hello_world.c文件为hello_world可执行文件,并链接数学库
同时编译多个文件
gcc -o hello_world hello_world.c hello_world2.c #编译hello_world.c和hello_world2.c文件为hello_world可执行文件
gcc -c hello_world.c hello_world2.c #编译hello_world.c和hello_world2.c文件为hello_world.o和hello_world2.o目标文件
选项-o用于指定要生成的结果文件,后面跟的就是结果文件名字。o是output的意思,不是目标的意思。结果文件可能是预处理文件、汇编文件、目标文件或者最终可执行文件。
Git
git真是一个非常好用的版本管理工具,发明者太强了没办法!
相信同学们经过oopre
后基本上对于git
的基本用法已经了如指掌了,这里包括
- git add . 添加修改文件到暂存区
- git commit -m “message”提交文件到版本库
- git push 提交到远程仓库
同时还包括一些基本的分支的操作
- git checkout -b new_branch
但是git
的更多高阶的用法其实还是不够熟悉,大多数还是需要查询相关资料进行使用。
这里推荐一个可视化git学习网站:Learn Git Branching
同时我这里整理了一下一些git 常用的指令
基本操作
git init
初始化一个仓库git clone
克隆一个仓库git add
添加文件到暂存区git commit
提交文件到仓库git status
查看仓库状态git diff
查看文件差异git log
查看提交日志git reset
重置仓库git rm
删除文件git mv
移动文件git branch
查看分支
分支操作
git branch
查看分支git checkout
切换分支git merge
合并分支git rebase
变基分支git cherry-pick
挑选提交git tag
标记提交git stash
暂存工作区git fetch
获取远程分支git pull
拉取远程分支git push
推送远程分支git remote
管理远程仓库git submodule
管理子模块git worktree
管理工作树git reflog
查看引用日志git bisect
二分查找git blame
查看文件作者git grep
查找文件内容git log
查看提交日志git show
查看提交详情
高级操作
git filter-branch
过滤分支git subcommand
子命令git rerere
重用冲突解决git gc
垃圾回收git fsck
检查仓库git prune
删除无用对象
git 版本回退
git reset --hard HEAD^
回退到上一个版本git reset --hard HEAD^^
回退到上上一个版本git reset --hard HEAD~100
回退到上100个版本git reset --hard commit_id
回退到指定版本git reflog
查看命令历史git reset --hard commit_id
回退到指定版本git reset --hard HEAD@{n}
回退到指定版本git reset --hard ORIG_HEAD
回退到上一个版本git reset --hard
回退到上一个版本
配置
git config --global user.name "Your Name"
设置用户名- `git config --global user.email "
git config --global core.editor "vim"
设置编辑器git config --global merge.tool "vimdiff"
设置合并工具git config --global color.ui true
设置颜色git config --global alias.st status
设置别名git config --global alias.co checkout
设置别名git config --global alias.ci commit
设置别名git config --global alias.br branch
设置别名git config --global alias.unstage "reset HEAD"
设置别名
Shell脚本
这个对于我自己来说也是一个比较大的难点!!主要对于一些特殊字符的用法不了解,其中包括小括号,中括号,大括号,单引号,反引号,双引号
我觉得把这个讲清楚真的非常重要,其次就是了解一些基本的变量、控制结构(条件结构,循环结构)基本上就能够懂得基本的用法了
其中稍微高阶一点,也是shell作为一个脚本型语言的特色就是其参数传递了
同时还有一些比较困难的指令的使用,包括
grep awk sed
虽然可以通过
man
来了解大部分
shell脚本
shell脚本是一个用于执行命令的脚本文件
- 在脚本中在第一行添加
#!/bin/bash
可以指定脚本使用的shell - 运行脚本
- 通过
chmod +x script.sh
添加执行权限后,./script.sh
运行脚本 sh script.sh
运行脚本./script.sh
运行脚本source script.sh
运行脚本
- 通过
- 参数
$0
脚本名$1
第一个参数$2
第二个参数$#
参数个数$*
所有参数,所有参数都是一个字符串$@
所有参数,每个参数都是一个独立的字符串$$
脚本的进程号$?
上一个命令的返回值$!
后台运行的最后一个进程的进程号
- 函数
function_name(){...}
定义函数function_name
调用函数return
返回值
- 控制结构
if...then...fi
条件语句case...esac
多条件语句for...do...done
循环语句while...do...done
循环语句until...do...done
循环语句break
跳出循环continue
跳过本次循环exit
退出脚本trap
捕获信号eval
执行命令exec
执行命令let
执行算术运算select
选择语句shift
移动参数source
执行脚本test
测试语句time
计时type
查找命令ulimit
设置资源限制
- 关系运算符
-eq
等于-ne
不等于-gt
大于-lt
小于-ge
大于等于-le
小于等于=
字符串相等!=
字符串不相等-z
字符串为空-n
字符串不为空-e
文件存在-f
文件存在且是普通文件-d
文件存在且是目录-s
文件存在且不为空-r
文件存在且可读
grep
awk
sed
实验体会
我觉得通过本次实验自己对于一些工具包括vim tmux
更加熟悉了,同时对于shell
脚本的撰写也更加熟悉了。学到了很多东西!!!
当然还有一点体会就是对于命令的细节还是要更加了解一点,比如echo
会自动加入换行符,真的被狠狠背刺了啊啊啊啊!!
前面没有提到,这里分享一下自己学习tmux
的经验
tmux is terminal multiplexer
虽然你可以打开多个终端,但是tmux帅啊!!
创建会话 creating tmux sessions
tmux
这样会打开一个新的页面也该窗口
退出
exit
增加一个命名:
tmux new -s test
创建新的tmux窗口creating new tmux windows
Ctrl-b c
Ctrl-b
在tmux里面相当于是一个命令前缀
在两个tmux窗口之间切换 switching between tmux windows
Ctrl-b n
这样会顺序遍历已经创建的窗口
Ctrl-b 2
你可以注意到这个窗口的名字叫做bash,是因为目前是正在运行进程,如果你某一个窗口运行htop
,那么那个窗口的名字就是htop
如果你想要设置一个不会改变的窗口命名
Ctrl-b ,
离开一个会话detaching from a tmux session
Ctrl-b d
连接一个会话attaching to a tmus session
tmux a
如果需要重新新建一个任务可以
Ctrl-b new -s coding
// 也就是前面的新建一个session的操作
列举所有tmux会话listing tmux sessions
tmux ls
如果想要连接某一个session
,可以
tmux a -t test
可以再几个session
之间切换
Ctrl-b s
窗格操作
划分窗格
tmux split-window
命令用来划分窗格。
# 划分上下两个窗格 $ tmux split-window # 划分左右两个窗格 $ tmux split-window -h
移动光标
tmux select-pane
命令用来移动光标位置。
# 光标切换到上方窗格 $ tmux select-pane -U # 光标切换到下方窗格 $ tmux select-pane -D # 光标切换到左边窗格 $ tmux select-pane -L # 光标切换到右边窗格 $ tmux select-pane -R
交换窗格位置
tmux swap-pane
命令用来交换窗格位置。
# 当前窗格上移 $ tmux swap-pane -U # 当前窗格下移 $ tmux swap-pane -D
窗格快捷键
下面是一些窗格操作的快捷键。
Ctrl+b %
:划分左右两个窗格。Ctrl+b "
:划分上下两个窗格。Ctrl+b <arrow key>
:光标切换到其他窗格。<arrow key>
是指向要切换到的窗格的方向键,比如切换到下方窗格,就按方向键↓
。Ctrl+b ;
:光标切换到上一个窗格。Ctrl+b o
:光标切换到下一个窗格。Ctrl+b {
:当前窗格与上一个窗格交换位置。Ctrl+b }
:当前窗格与下一个窗格交换位置。Ctrl+b Ctrl+o
:所有窗格向前移动一个位置,第一个窗格变成最后一个窗格。Ctrl+b Alt+o
:所有窗格向后移动一个位置,最后一个窗格变成第一个窗格。Ctrl+b x
:关闭当前窗格。Ctrl+b !
:将当前窗格拆分为一个独立窗口。Ctrl+b z
:当前窗格全屏显示,再使用一次会变回原来大小。Ctrl+b Ctrl+<arrow key>
:按箭头方向调整窗格大小。Ctrl+b q
:显示窗格编号。
获取帮助getting help with tmux
Ctrl-b ?
或者使用
man tmux
reference