Fari

Shell

体验一下zsh

linux人机交互使用的是shell,shell是一个统称,具体的,比如 sh、bash、zsh等,一般来说,linux都默认安装bash作为默认shell,mac默认为zsh,今天来体验一下zsh。

zsh在使用ohmyzsh进行配置后有很多很花的玩法,界面主题也花里胡哨,各种跳转补全啥的也花里胡哨

安装

ubuntu中可以直接使用命令安装:

sudo apt install zsh

安装完成后,就能使用 zsh 命令切换到zsh了,因为是使用bash打开的zsh,所以bash中的环境变量也会被zsh继承。当然,也可以通过以下命令将zsh设置为默认shell,这样的话下次再打开shell就是zsh了(例如如果没有设置默认,重新进入shell后又会回到bash):

sudo chsh -s /bin/zsh

配置

同bash有自己的配置文件 ~/.bashrc一样,zsh也有自己的配置文件 .zshrc,它们本质上都是一个shell启动时的执行脚本,关于shell的配置文件,详见这里(注:zsh并不读取/etc/profile环境配置,而是使用/etc/zsh/zprofile作为环境变量配置)

zsh同bash一样,可以有很多自定义配置,但往往个人配置起来耗时费力,所以有个项目可以帮你减少这些配置 “ohmyzsh”,它实际上就是一个shell脚本,运行这个脚本之后它会替换掉你home目录下的 .zshrc 文件,并且创建一些列文件夹用于保存要安装的插件、主题等。

根据ohmyzsh官网说明安装很简单:

# 官网提供了很多种安装方式,但本质上都是下载一个shell脚本并执行
sh -c "$(curl -fsSL https://raw.githubusercontent.com/ohmyzsh/ohmyzsh/master/tools/install.sh)"

执行完成后它会将你原本的.zshrc文件重命名为.zshrc.pre-oh-my-zsh,并在home目录下创建一个.oh-my-zsh文件夹,里面存放zsh下载的主题、插件等文件,并创建环境变量 $ZSH 指向该文件夹

主题和插件

安装ohmyzsh之后,打开.zshrc文件,若要修改主题,找到变量 ZSH_THEME,改变其值即可,可以修改的主题名详见这里,每个主题都有截图

若要安装插件,则找到plugins变量,它是一个数组,将要安装的插件名写到里面即可(插件之间使用空格、tab、换行区分,不能使用逗号)。可以直接写名称的插件见这里(事实上,这些插件都已经下载好了并存放在~/.oh-my-zsh/plugins/目录下)

有些插件不是官方提供的,可以直接将插件目录复制到~/.oh-my-zsh/plugins/目录下,然后在配置种写上该名称即可。

推荐主题和插件

主题看很多人用的是 agnoster,安装这个主题之前通常还要安装一个字符集,不然显示可能不正常 sudo apt-get install fonts-powerline,vscode终端显示异常解决办法见下文

插件一般安装:

git:在git仓库文件夹下会有很多关于git状态的提示

zsh-autosuggestions:这个插件可以在输入命令时,以灰色字体提示历史命令,免去了按 ctrl+r 操作,需要下载后安装

  1. 下载插件到~/.oh-my-zsh/plugins/目录下:git clone https://github.com/zsh-users/zsh-autosuggestions ${ZSH_CUSTOM:-~/.oh-my-zsh/custom}/plugins/zsh-autosuggestions

  2. .zshrc 的plugins中加上 zsh-autosuggestions 即可

  3. 执行 source .zshrc 使其生效

注:由于有些终端(xterm或者screen等)默认只有8色,不支持很多其他颜色,故该插件实际显示效果上会有bug,解决办法:在 ~/.zshrc 中加入下面这段代码修改默认终端:

# 原本为 xterm/screen,现修改为xterm-256color将支持更多颜色,可以使用 tput colors 命令查看支持颜色数量
export TERM=xterm-256color

CommandNotFoundError: Your shell has not been properly configured to use 'conda activate'

出现问题

远程ubuntu主机安装有anaconda,ssh远程登陆,发现命令提示符行首没有conda环境名称。输入 conda activate env-name 提示shell没有配置正确,并建议使用 conda init 命令初始化shell,但使用该命令后仍然无效

但使用 source activate env-name 可行

解决方案

以下六个方法对我均有效,为什么有效见 原因 部分的分析,其中,前五种方法为临时解决方案,第六种为永久解决方案

方法一:使用 source 命令激活环境

source activate env-name

方法二:

eval "$(conda shell.bash hook)"
conda activate <env-name>

方法三:

source ~/anaconda3/etc/profile.d/conda.sh
conda activate my_env

方法四:

bash
conda activate my_env

方法五:

source ~/.bashrc
conda activate my_env

方法六(永久生效):

~/.bash_profile 中(若没有则创建)添加以下代码

# if running bash  
if [ -n "$BASH_VERSION" ]; then  
    # include .bashrc if it exists  
    if [ -f "$HOME/.bashrc" ]; then  
        . "$HOME/.bashrc"  
    fi  
fi  

原因

我出现该问题的原因是环境变量设置的问题,我也有看到说若之前没有正确退出conda环境就退出shell也可能出现该问题,见这里

linux自动重试出错命令

例如国内使用默认channel安装pytorch比较困难,很容易网络连接超时,所以需要写一个脚本不断重试,记录一下刚写的一个简单脚本

#!/bin/bash

while true;do
        python -m pip install torch==1.8.2 torchvision==0.9.2 torchaudio==0.8.2 --extra-index-url https://download.pytorch.org/whl/lts/1.8/cu111
        if [[ $? -eq 0 ]];then
                break
        fi
done

也可以不适用shell脚本,一行命令搞定

bash -c "while true; do command && break; done"

对shell脚本的逐行批注:

#!/bin/bash 用于指定执行的shell,否则将使用默认shell执行(sh、bash等),出现不可控的情况

while true;do 有的时候会看到没有分号的写法,但do在下一行,两种写法都可以,这里的分号起断句的作用

python -m pip install 也能看到直接写 pip install 的,区别在于用 python -m 执行的话会使用与python环境对应的pip,而直接使用pip install的话就使用的是环境变量中的pip,但有的时候和python环境还不是对应的

if [[ command ]];then 也能看到只用单个中括号的[],一般来说两者都行,但单括号的兼容性更好,而双括号的只支持部分常用的shell,还要注意command两边的空格

$? -eq 0 $用于获取变量,$? 可以获取上一条指令执行的结果,如果执行成功则返回0,否则为其他数值。-eq 就是 ==,其他的还有 -ne 表示 不等于,-gt 表示大于,-lt 表示小于等等

shell中[ ]与\[\[ \] ]的区别

Shell if 条件判断