IFS
significa "separador de campo interno". Ele é usado pelo shell para determinar como fazer a divisão de palavras, i. e. como reconhecer limites de palavras.
Tente isso em um shell como o bash (outras shells podem lidar com isso de forma diferente, por exemplo zsh):
mystring="foo:bar baz rab"
for word in $mystring; do
echo "Word: $word"
done
O valor padrão para IFS
consiste em caracteres de espaço em branco (para ser preciso: espaço, tabulação e nova linha). Cada caractere pode ser um limite de palavra. Portanto, com o valor padrão de IFS
, o loop acima será impresso:
Word: foo:bar
Word: baz
Word: rab
Em outras palavras, o shell pensa que o espaço em branco é um limite de palavra.
Agora, tente definir IFS=:
antes de executar o loop. Desta vez, o resultado é:
Word: foo
Word: bar baz rab
Agora, o shell também divide mystring
em palavras - mas agora ele trata apenas dois pontos como o limite da palavra.
O primeiro caractere de IFS
é especial: é usado para delimitar palavras na saída ao usar a variável especial $*
(exemplo obtido do Guia avançado de script Bash , onde você também pode encontrar mais informações sobre variáveis especiais como essa):
$ bash -c 'set w x y z; IFS=":-;"; echo "$*"'
w:x:y:z
Compare com:
$ bash -c 'set w x y z; IFS="-:;"; echo "$*"'
w-x-y-z
Observe que, nos dois exemplos, o shell ainda tratará todos os caracteres :
, -
e ;
como limites de palavras. A única coisa que muda é o comportamento de $*
.
Outra coisa importante a saber é como o chamado "espaço em branco do IFS" é tratado . Basicamente, assim que IFS
incluir caracteres de espaço em branco, os espaços em branco iniciais e finais são removidos da string para serem divididos antes do processamento e uma seqüência de caracteres consecutivos de espaços em branco também delimita os campos. No entanto, isso só se aplica aos caracteres de espaço em branco que estão realmente presentes em IFS
.
Por exemplo, vamos ver a string "a:b:: c d "
(espaço à direita e dois caracteres de espaço entre c
e d
).
- Com
IFS=:
, ele seria dividido em quatro campos:"a"
,"b"
,""
(string vazia) e" c d "
(novamente, dois espaços entrec
ed
). Observe o espaço em branco inicial e final no último campo. - Com
IFS=' :'
, seria dividido em cinco campos:"a"
,"b"
,""
(sequência vazia),"c"
e"d"
. Nenhum espaço em branco à esquerda e à direita em qualquer lugar.
Observe como vários caracteres de espaço em branco consecutivos delimitam dois campos no segundo exemplo, enquanto vários pontos consecutivos não (uma vez que não são caracteres de espaço em branco).
Quanto a IFS=$'\n'
, essa é uma sintaxe ksh93
também suportada por bash
, zsh
, mksh
e FreeBSD sh
(com variações entre todos os shells). Citando o bash manpage:
Words of the form $'string' are treated specially. The word expands to "string", with backslash-escaped characters replaced as specified by the ANSI C standard.
\n
é a sequência de escape para uma nova linha, então IFS
acaba sendo definido para um único caractere de nova linha.