No primeiro artigo que publiquei sobre vetores, eu disse que o espaço é um separador de elementos. Eu não menti, simplesmente disse uma 'meia-verdade'...
Na verdade o espaço não é um separador por obrigação, e sim porque uma variável guarda qual é o valor desse separador. Não vou explicar sobre ela, pois acabaria confundindo mais você. Mas se quiser mesmo saber, leia essa página:
O que podemos fazer com essa belezinha? Coisas como...
Modificar o separador de elementos:
$ export IFS=:
Atribuindo o conteúdo da variável PATH como elementos de um vetor path:
$ path=($PATH) # vetor path
Exibindo o seu conteúdo:
$ echo ${path[@]}
/usr/local/bin /usr/bin /bin /usr/X11R6/bin /usr/games /opt/kde/bin /opt/rox/bin /opt/xaralx/bin /opt/www/htdig/bin /usr/lib/java/bin /usr/lib/java/jre/bin /usr/lib/java/bin /usr/lib/java/jre/bin /opt/kde/bin /usr/lib/qt/bin /usr/share/texmf/bin . /home/tenchi/.local/bin /opt/rox/bin/
Com isso, é possível saber quantos diretórios estão no nosso PATH:
$ echo ${#path[@]}
20
Bem, nem sempre isso é dado como certo, pois, por exemplo, os diretórios /usr/lib/java/jre/bin e /usr/lib/java/bin aparecem cada um, duas vezes na lista ;)
Isso funciona pra todos os comandos que lêem o espaço como separador, como o for:
Basta modificar o IFS para ler o dois-pontos (:) como separador de elementos, como acontece com as variáveis PATH, MANPATH, etc... (Use 'set | grep PATH' para ver quais).
Agora, um exemplo de construção bem bizarra e inútil:
$ IFS=/
$ for inutil in $MANPATH; do echo $inutil ; done | tr -d :
usr
local
man
usr
man
usr
X11R6
man
usr
lib
java
man
usr
lib
java
man
opt
kde
man
usr
lib
qt
doc
man
usr
share
texmf
man
O que isso faz?
Exibe o conteúdo da variável $MANPATH, separando cada termo como sendo os elementos separados por uma barra (/). Em seguida, joga essa saída para o tr, que apaga (-d) os dois-pontos que aparecem.
Observação: Esse comando foi totalmente inútil, e serviu somente como exemplo.
Mas, se quisermos fazer essa variável voltar "ao normal"?
Bem, simplesmente aniquilá-la:
$ unset IFS
Observação: Não tenho provas científicas de que ao aniquilar o IFS ele volte ao valor default. Simplesmente funcionou aqui.
Segundo o site
Bar do Júlio Neves, deve-se atribuir um caractere tab e um enter nessa variável. Aqui eu não notei a diferença. Acredito que eu possa estar errado, então confira você mesmo.
Lembrando que esse unset deve ser colocado de preferência logo após a atribuição do vetor, para que não atrapalhe nos outros comandos do seu script:
$ IFS=:
$ Vetor=($PATH)
$ unset IFS
$ echo ${Vetor[0]}
/usr/local/bin
Se não fizéssemos a atribuição de IFS:
$ Vetor=($PATH)
$ unset IFS # desnecessário
$ echo ${Vetor[0]}
/usr/local/bin:/usr/bin:/bin:/usr/X11R6/bin:/usr/games:/opt/kde/bin: /opt/rox/bin:/opt/xaralx/bin:/opt/www/htdig/bin:/usr/lib/java/bin: /usr/lib/java/jre/bin:/usr/lib/java/bin:/usr/lib/java/jre/bin:/opt/kde/bin: /usr/lib/qt/bin:/usr/share/texmf/bin:.:/home/tenchi/.local/bin:/opt/rox/bin/
Agora, compare os comandos acima e perceba as diferenças.
Nota: Dentro das funções, defina a variável IFS como sendo local. Exemplo:
$ Teste()
>
{
>
local IFS=:
> <conteúdo_da_função>
>
}
Assim, ao sair da função, a variável IFS estará novinha em folha, sem nenhuma modificação, pois as variáveis locais são automaticamente destruídas quando acaba a função... ;)
Observações:
- Essa sinal '>' é o que chamamos de segundo prompt do bash.
- Ele pode ser modificado quando modificamos a variável PS2:
$ PS2='^ '
$ Teste()
^
{
^
echo oi
^
}
Além deste, existem pelo menos mais três outros prompts no bash:
- PS1 : é o prompt principal, normalmente '$', ou algo personalizado, que exibe o seu usuário, hostname, etc.
- PS3 : é o prompt do comando select. Normalmente '#? '.
- PS4 : é o prompt que aparece quando estamos depurando um script. Normalmente é um sinal de mais (+). Para isso, execute:
$ bash -vc script.sh
Bem, se quiserem saber mais, leiam esta dica: