首页 > 编程笔记 > Linux笔记 阅读:7

Linux系统环境变量详解(附带实例)

在 Linux 中,一般通过系统环境变量来配置操作系统的环境,如提示符、在执行命令时用来查找命令的命令绝对路径、用户家目录、用户 ID、当前所在目录等。这些系统默认的环境变量的变量名是固定的,变量的作用也是固定的,我们只能修改变量值,系统环境变量的变量名或作用都是不能修改的。

系统中默认有很多环境变量,下面来详细了解这些系统默认的环境变量的作用。
[root@localhost~]# env
# 查看当前系统环境变量
SHELL=/bin/bash  # 当前使用的解释器类型
HISTCONTROL=ignoredups  # 历史命令记录方式,ignoredups 表示忽略重复的历史命令
HISTSIZE=1000  # 历史命令记录条数
HOSTNAME=localhost  # 简写主机名
PWD=/root  # 用户当前所在目录
LOGNAME=root                  ←表示当前用户名,可以在记录日志时调用该变量的值
XDG_SESSION_TYPE=tty           ←表示所使用的会话类型,在使用 Xshell 远程连接或字符界面登录时显示结果为 tty,使用图形化本地登录后打开终端时显示 wayland,表示图形显示协议
HOME=/root                     ←当前用户家目录
LANG=zh_CN.UTF-8               ←当前所使用的语系变量
LS_COLORS=rs=0:di=01;34:ln=01;36:mh=00:pi=40;33:so=01;35:bd=40;33;01:cd=40;33;01:or=01;37;41:su=37;41:sg=30;43:ca=
30;41:tw=30;42:ow=34;42:st=37;44:ex=01;32:*.tar=01;31:*.tgz=01;31:*.arj=01;31:*.taz=01;31:*.lzma=01;31:*.lz4=01;31:*.lzh=01;
*.lz=01;31:*.tlz=01;31:*.txz=01;31:*.tzo=01;31:*.t7z=01;31:*.zip=01;31:*.z=01;31:*.dz=01;31:*.gz=01;31:*.lrz=01;31:*.xz=01;31:*.zst=01;31:*.bz2=01;31:*.bz=01;31:*.tbz=01;31:*.tbz2=01;31:*.tz=01;31:*.deb=01;31:*.rpm=01;31:*.jar=01
31:*.war=01;31:*.ear=01;31:*.sar=01;31:*.rar=01;31:*.alz=01;31:*.ace=01;31:*.zoo=01;31:*.cpio=01;31:*.7z=01;31:*.rz=01;31:*.cab=01;31:
*.wim=01;31:*.swm=01;31:*.dwm=01;31:*.esd=01;31:*.jpg=01;35:*.jpeg=01;35:*.mjpg=01;35:*.mjpeg=01;35:*.gif=01;35:*.bmp=01;35
*.pbm=01;35:*.pgm=01;35:*.ppm=01;35:*.tga=01;35:*.xbm=01;35:*.xpm=01;35:*.tif=01;35:*.tiff=01;35:*.svg=01;35:*.svgz=01;35:*.mng=01;35
*.pcx=01;35:*.mov=01;35:*.mpg=01;35:*.mpeg=01;35:*.m2v=01;35:*.mkv=01;35:*.webm=01;35:*.webp=01;35:*.ogm=01;35:*.mp4=01;35
*.mpv=01;35:*.vob=01;35:*.qt=01;35:*.nuv=01;35:*.wmv=01;35:*.asf=01;35:*.rm=01;35:*.rmvb=01;35:*.flc=01;35:*.avi=01;35:*.fli=01;35:*.flv=01;35
*.f=01;35:*.gl=01;35:*.dl=01;35:*xcf=01;35:*.xwd=01;35:*.yuv=01;35:*.cgm=01;35:*.emf=01;35:*.ogv=01;35:*.ogx=01;35:*.aac=01;36:*.au=01;
*.flac=01;36:*.m4a=01;36:*.mid=01;36:*.midi=01;36:*.mka=01;36:*.mp3=01;36:*.mpc=01;36:*.ogg=01;36:*.ra=01;36:*.wav=01;36:*.oga=01;36
*.opus=01;36:*.spx=01;36:*.xspf=01;36:             ←定义终端显示
SSH_CONNECTION=192.168.5.1 62058 192.168.5.131 22     ←当前 ssh 远程连接的 IP 端口号等信息
TERM=xterm                       ←终端类型,远程登录为 xterm,字符本地登录为 Linux
LESSOPEN=||/usr/bin/lesspipe %s  ←less命令预处理脚本,可以提供查看压缩文件功能
USER=root                        ←当前登录用户
SHELVL=0                         ←每运行一个 bash,此数字递增 1
SSH_CLIENT=192.168.5.1 62058 22  ←ssh 客户端 IP 端口信息
PATH=/root/local/bin:/root/bin:/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin
←在执行命令时,命令可执行文件查找目录
DBUS_SESSION_BUS_ADDRESS=unix:path=/run/user/0/bus  ←用于指定会话的总线地址
MAIL=/var/spool/mail/root        ←用户邮箱
SSH_TTY=/dev/pts/0               ←当前所在终端名
BASH_FUNC_which%%=() { ( alias;
eval ${which declare} ) | /usr/bin/which --tty-only --read-alias --read-functions --show-tilde --show-dotglob "$@"
}                  ←声明环境变量的函数
_=/usr/bin/env     ←上次执行命令的参数或命令本身
在执行 env 命令后,可以查询到系统中默认存在的环境变量和我们声明的环境变量。另外,系统中还存在一些虽然不是 env 输出但却和当前运行环境相关的变量。

这些变量只能用 set 命令来查看,这里只列出重要的内容,具体如下:
[root@localhost ~]# set
BASH=/bin/bash                 ←Bash 的位置
BASH_VERSION='5.1.8(1)-release' ←Bash 的主要、次要版本等相关信息
LS_COLORS=/etc/DIR_COLORS       ←颜色记录文件
HISTFILE=/root/.bash_history     ←历史命令保存文件
HISTFILESIZE=1000               ←在文件中记录的历史命令最大条数
HISTSIZE=1000                   ←在缓存中记录的历史命令最大条数
LANG=zh_CN.UTF-8               ←语系变量
MACHTYPE=x86_64-redhat-linux-gnu ←软件类型是 x86_64 类型
MAILCHECK=60                    ←每隔 60 秒扫描新邮件
PPID=1290                       ←当前进程的父进程 PID
PS1='[\\u@\\h \\W]\\$'          ←命令提示符
PS2=>'                         ←如果命令在一行中没有输入完成,那么下一行使用 “>” 作为命令提示符
UID=0                          ←当前用户的 UID
接下来结合 env 命令和 set 命令的返回结果,继续查看有哪些重要并需要修改的变量。

Linux PATH变量:系统查找命令的路径

我们知道 /usr/bin/ 和 /usr/sbin/ 目录是系统用来保存命令的目录,在这两个目录中,我们日常执行的 ls、cat、cp、mkdir 等命令都能找到对应的可执行文件。那么,为什么在我们执行命令时不需要指定命令所在的目录呢?这其实就是 PATH 变量的功劳了。

在我们执行命令时,系统默认会按照 PATH 变量记录的目录查找对应的命令可执行文件,这样执行的命令就不需要再加入命令所在的绝对路径了。
[root@localhost ~]# echo $PATH
/root/bin:/root/bin:/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin
当我们执行 ls 命令时,系统会默认根据变量 PATH 记录的目录查询 ls 可执行文件。在 PATH 的路径上,以“:”为目录之间的分隔符。

如果我们想在原有 PATH 路径的基础上增加一些查询可执行文件的路径,就可以使用变量叠加的方式,执行结果如下:
[root@localhost ~]# PATH=${PATH}:/root
#在变量PATH的后面,加入/root目录
[root@localhost ~]# echo $PATH
/root:/root/bin:/root/bin:/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/root

#查询PATH的值,变量叠加生效了
[root@localhost ~]# export PATH
#在变量叠加后再次声明环境变量,以此避免修改过的 PATH 在子 shell 中不生效
在原有路径的基础上加入 /root 目录作为命令执行过程中的查找目录,这样一来,我们写在 /root/ 目录中的脚本就可以不添加路径直接运行了。

对于 PATH,需要注意以下几点:

Linux PS1变量:命令提示符设置

PS1 变量用来定义命令行的提示符,可以按照自己的需求来定义自己喜欢的提示符。

PS1 变量可以支持以下选项:
这些选项应该怎么使用呢?先看看 PS1 变量的默认值,具体如下:
[root@localhost ~]# echo $PS1
[\\u@\\h \\W]\\$
#默认的提示符是显示“用户名@简写主机名 最后所在目录提示符”
在 PS1 变量中,如果是可以解释的符号,如“\\u”、“\\h”等,就是显示这个符号的作用;而某些符号是不具备特殊含义直接输出的,如“@”或“空格”,就按照原符号输出。

我们修改一下 PS1 变量,看看会出现什么情况:
[root@localhost ~]# PS1='[\\u@\\h \\w]\\$'
#修改提示符为[用户名@当前时间 当前所在完整目录提示符]
[root@12:26:00~]# cd /usr/local/src/
#切换到当前所在目录,因为在家目录中是看不出来区别的
[root@12:26:00/usr/local/src/#]
#提示符按照 PS1 变量的修改发生了变化

这里要注意,PS1 变量的值要使用单引号包含,否则设置不生效,再举个例子:
[root@12:26:08/usr/local/src/# PS1='[\\u@\\h \\# \\W]\\$'
[root@12:26 上午 localhost 31 src/#
#提示符又变了。\@:时间格式是 HH:MM am/pm;#:会显示执行了多少条命令

PS1 变量可以自由定制,从中好像看到了一点 Linux 系统可以自由定制和修改的影子。不过,在适应了原有命令提示符以后,如果换一个还是觉得不太习惯,就改回默认的提示符吧,命令如下:
[root@04:53 上午 localhost 31 src/# PS1='[\\u@\\h \\W]\\$'
[root@localhost src/
注意,这些提示符的修改同样是临时生效的,一旦注销或重启系统就会消失。要想使其永久生效,必须写入环境变量配置文件。

Linux LANG语系变量

LANG 变量定义了 Linux 的主语系环境,这个变量的默认值如下:
[root@localhost src/]# echo $LANG
zh_CN.UTF-8
注意,如果使用本机纯字符界面登录,那么 LANG 的值是“en_US.UTF-8”,这是由于纯字符界面不支持中文显示,Linux 系统默认把纯字符界面的语系环境改成了英文。但如果使用远程工具或图形界面登录系统,那么 LANG 的值是“zh_CN.UTF-8”,这两种登录方式都可以正确显示中文。

因为我们在安装 Linux 系统时选择的是中文安装,所以默认的主语系变量是“zh_CN.UTF-8”。那么,Linux 系统到底支持多少种语系呢?可以使用以下命令查询:
[root@localhost ~]# locale -a
C
C.utf8
POSIX
zh_CN
zh_CN.gb18030
zh_CN.gbk
zh_CN.utf8
zh_HK
zh_HK.utf8
zh_SG
zh_SG.gbk
zh_SG.utf8
zh_TW
zh_TW.euctw
zh_TW.utf8

既然 Linux 系统支持多种语系,那么当前系统使用的到底是什么语系呢?可以使用 locale 命令直接查询,具体如下:
[root@localhost ~]# locale
LANG=zh_CN.UTF-8

LC_CTYPE="zh_CN.UTF-8"
LC_NUMERIC="zh_CN.UTF-8"
LC_TIME="zh_CN.UTF-8"
LC_COLLATE="zh_CN.UTF-8"
LC_MONETARY="zh_CN.UTF-8"
LC_MESSAGES="zh_CN.UTF-8"
LC_PAPER="zh_CN.UTF-8"
LC_NAME="zh_CN.UTF-8"
LC_ADDRESS="zh_CN.UTF-8"
LC_TELEPHONE="zh_CN.UTF-8"
LC_MEASUREMENT="zh_CN.UTF-8"
LC_IDENTIFICATION="zh_CN.UTF-8"
LC_ALL=

在 Linux 系统中,语系主要是通过以上这些变量来设置的,这里只需知道 LANG 变量和 LC_ALL 变量即可,其他变量会根据这两个变量的值而发生变化。LANG 变量是定义系统主语系的变量,LC_ALL 变量是定义整体语系的变量,一般使用 LANG 变量来定义系统语系。

我们还要通过文件 /etc/locale.conf 定义系统的默认语系,查看这个文件的内容,具体如下:
[root@localhost ~]# cat /etc/locale.conf
LANG="zh_CN.UTF-8"
又是当前系统语系,又是默认语系,有没有快晕倒的感觉?解释一下,我们可以这样理解:默认语系是下次重启之后系统所使用的语系,而当前系统语系是当前系统所使用的语系。如果系统重启,就会从默认语系配置文件 /etc/locale.conf 中读出语系,然后赋予 LANG 变量,让这个语系生效。

也就是说,LANG 变量定义的语系只对当前系统生效,如果想让语系永久生效,就要修改 /etc/locale.conf 文件。

说到这里,我们需要解释一下 Linux 系统的中文支持问题。是不是只要定义了语系为中文,如 zh_CN.UTF-8,就可以正确显示中文了呢?要想正确显示中文,需要满足以下三个条件。
• 安装了中文编码和中文字体(我们在安装的时候要求大家采用中文安装,已经安装了中文编码和字体);
• 系统语系设置为中文语系;
• 操作终端必须支持中文显示。

我们的操作终端都支持中文吗?这要分情况,如果是在图形界面中,或者使用远程连接工具(如 SecureCRT、Xshell 等),这些终端都支持中文编码,只要语系设置正确,中文显示就没有问题,举个例子:
[root@localhost ~]# df -h
文件系统          容量   已用    可用  已用%  挂载点
devtmpfs          951M     0   951M    0% /dev
tmpfs             971M     0   971M    0% /dev/shm
tmpfs             389M  5.7M   383M    2% /run
/dev/mapper/root   17G  1.5G    16G    9% /
/dev/sda1         1014M   166M   849M   17% /boot
tmpfs             195M     0   195M    0% /run/user/0
#在df命令结果中,我们可以看到中文能够正常显示
但如果是纯字符界面(本地终端 tty1~tty6),就不能显示中文,因为 Linux 系统的纯字符界面不能显示中文这样复杂的编码。举个例子,如果是在纯字符界面呢?虽然 Linux 系统是使用中文安装的,但纯字符界面的语系却是“en_US.UTF-8”,如下图所示。


图 1 字符界面本地登录的默认语系

我们将语系强制更改为中文,看看会出现什么情况,如下图所示。


图 2 字符界面本地登录设置中文语系

可以发现,如果强行在纯字符界面中设置中文语系,那么本该显示中文字体的部分会出现乱码。

相关文章