Como usar o comando Bash printf no Linux

Publicados: 2022-06-25
Um terminal Linux em um fundo azul.
fatmawati achmad zaenuri/Shutterstock.com

O comando Bash printf permite gravar em uma janela de terminal Linux com controle mais preciso e mais opções de formatação do que o comando echo fornece. Até as peculiaridades do printf podem ser úteis.

Escrevendo em um Terminal

É uma das partes mais básicas da interação com um programa. O programa escreve algo na tela e você lê. Mesmo levando em consideração a convenção derivada do Unix e mantida pelo Linux de programas de linha de comando serem o mais concisos possível - muitos só gravam no terminal se algo der errado. Dizer ao usuário o que está acontecendo, ou está prestes a acontecer, ou acabou de acontecer é uma primitiva de programação essencial.

Como usar o comando Echo no Linux
RELACIONADO Como usar o comando Echo no Linux

O shell Bash tem o comando echo que pode escrever texto na janela do terminal. Ele pode manipular variáveis ​​e exibir seus valores se estiverem incluídos na string, e você pode usá-lo em scripts ou na linha de comando. Então, por que printf existe? O echo não cobre a coisa da escrita de texto? Bem, printf oferece funcionalidade além do simples ato de escrever strings em janelas de terminal. Ele permite formatar a saída com grande flexibilidade e também possui outros truques.

O comando Bash printf é modelado na função printf da linguagem C, mas há diferenças. Se você conhece C, precisa ficar atento a essas diferenças.

Escrevendo Strings Básicas

Vamos ver como echo e printf diferem quando escrevem strings no terminal.

 eco aqui estão algumas palavras
 printf aqui estão algumas palavras 

Usando echo e printf com palavras sem aspas

O comando echo imprime todas as palavras, mas printf imprime apenas a primeira palavra. Além disso, não há nova linha impressa por printf . A saída é colocada diretamente no prompt de comando. Mas, antes de mais nada, para que printf atue em todas as palavras, elas precisam ser citadas.

 eco aqui estão algumas palavras
 printf "aqui estão algumas palavras" 

Usando echo e printf com palavras entre aspas

Isso é melhor. Temos todas as palavras sendo impressas, mas ainda não recebemos uma nova linha. Isso porque com printf você só consegue uma nova linha se pedir uma. Isso pode parecer uma dor, mas permite que você decida se deve incluir um ou não. Para fazer com que printf emita uma nova linha, você precisa incluir “ \n ” em sua string. Esta é a sequência de escape “nova linha”.

 eco aqui estão algumas palavras
 printf "aqui estão algumas palavras\n" 

Usando echo e printf com palavras entre aspas e o caractere de nova linha

Às vezes você usará uma nova linha e às vezes não. Aqui está um caso em que uma instrução printf usa uma nova linha e a outra não.

 printf "Como fazer" && printf "Geek\n" 

Usando dois printfs para criar uma única linha de texto

Como o primeiro printf não imprime uma nova linha, a saída do segundo printf é posicionada imediatamente após “How-To” e na mesma linha. O segundo printf usa \n para imprimir uma nova linha. Isso faz com que o prompt de comando apareça na linha abaixo do texto impresso.

RELACIONADO: Como processar um arquivo linha por linha em um script Bash do Linux

Outros personagens de escape

Aqui estão mais alguns caracteres de escape que você pode usar. Você já viu “ \n ” em ação.

  • \n : Desce para uma nova linha.
  • \r : Imprime um retorno de carro. Isso envia o cursor de saída de volta ao início da linha atual.
  • \t : Imprime um caractere de tabulação.
  • \v : imprime um espaço de tabulação vertical.
  • \\ : Imprime um caractere de barra invertida.
  • \” : Imprime um caractere de cotação.
  • \b : Imprime um caractere de retrocesso.

O caractere de escape de retorno de carro move o cursor de volta ao início da linha atual .

 printf "O mel é a raiz de todo mal\rDinheiro\n" 

Usando o caractere de retorno de carro para voltar ao início da linha

O comando printf processa sua entrada da esquerda para a direita. A string é impressa como texto normal até que printf encontre o caractere de escape “ \r ”. O cursor de saída é movido de volta para o início da linha atual.

O processamento da string é retomado com a letra imediatamente atrás do caractere “ \r ”. Processar o restante faz com que printf imprima “Money”, substituindo a palavra “Honey”.

As aspas “ " ” são usadas para citar strings, e a barra invertida “ \ ” indica seqüências de escape. Se você quiser imprimir esses caracteres, precisará escapá-los com uma barra invertida. Isso diz ao printf para tratá-los como caracteres literais.

 printf "Esta é uma \tTab, esta é uma aspa \", e esta \\ é uma barra invertida\n" 

Caracteres de escape para que sejam tratados literalmente

Usando variáveis

Usar variáveis ​​com printf é muito semelhante a usá-las com echo . Para incluir uma variável, como esta variável de ambiente, preceda-a com o cifrão “ $ ” como de costume.

 printf "Diretório inicial: $HOME\n" 

Usando printf com uma variável de ambiente

RELACIONADO: Como trabalhar com variáveis ​​no Bash

Strings de formato

As strings de formato são strings que definem o formato da saída. Você fornece texto e outros valores como argumentos para a string de formato operar.

A string de formato pode incluir texto, sequências de escape e especificadores de formato . Os especificadores de formato informam ao printf que tipo de argumento esperar, como strings, inteiros ou caracteres.

Esses são os especificadores de formato mais comuns. Todos eles são precedidos por um sinal de porcentagem “ % ”. Para imprimir um sinal de porcentagem, use dois sinais de porcentagem juntos “ %% .”

  • %s : Imprime uma string.
  • %c : Imprime um único caractere.
  • %d : Imprime um inteiro.
  • %f : imprime um número de ponto flutuante.
  • %u : Imprime um inteiro sem sinal.
  • %o : Imprime um valor em octal.
  • %x : Imprime um valor em hexadecimal, em minúsculas.
  • %X : Imprime um valor em hexadecimal, em maiúsculas.
  • %e : Imprime um número de ponto flutuante em notação científica, em letras minúsculas.
  • %E : Imprime um número de ponto flutuante em notação científica, em letras maiúsculas.
  • %% : Imprime um símbolo de porcentagem “%”.
 printf "Como fazer %s\n" "Geek"
 printf "%s%s %s\n" "Como" "-Para" "Geek" 

Mostrando printf aceitando argumentos "muitos"

A string de formato no primeiro comando inclui algum texto próprio. Passamos a string “Geek” como argumento para printf . Ele corresponde e é impresso pelo especificador de formato “ %s ”. Observe que há apenas um espaço entre a string de formato e a string do argumento. Em C, você precisaria de uma vírgula para separá-los, mas com a versão Bash de printf , usar um espaço é suficiente.

A segunda string de formato contém apenas especificadores de formato e a sequência de escape de nova linha. Os três argumentos de string são consumidos por cada um dos especificadores de formato “ %s ” por sua vez. Novamente, em C, você precisa colocar uma vírgula entre cada argumento, mas o Bash printf nos permite esquecer isso.

Para imprimir diferentes tipos de argumentos, basta usar o especificador de formato apropriado. Aqui está uma rotina de conversão rápida de números criada usando printf . Vamos imprimir o valor 15 em notação decimal, octal e hexadecimal.

 printf "Dez: %d\nOut: %o\nHex: %x\n" 15 15 15 

usando printf para imprimir valores numéricos em diferentes notações de base

Vamos aparar um pouco para que o exemplo fique menos confuso.

 printf "Hex: %x\n" 15 

Imprimindo um valor hexadecimal

A maioria de nós está acostumada a ver valores hexadecimais em letras maiúsculas e com valores menores que 0x10 impressos com um zero à esquerda. Podemos conseguir isso usando o especificador de formato hexadecimal maiúsculo “ %X ” e colocando um especificador de largura entre o sinal de porcentagem “ % ” e o caractere “ X ”.

Isso informa ao printf a largura do campo em que o argumento deve ser impresso. O campo é preenchido com espaços. Com este formato, os valores de dois dígitos seriam impressos sem qualquer preenchimento.

 printf "Hex: %2X\n" 15 

imprimindo um valor hexadecimal em letras maiúsculas em um campo de 2 caracteres de largura

Agora obtemos um valor em maiúsculas, impresso com um espaço à esquerda. Podemos fazer printf preencher o campo com zeros em vez de espaços colocando um zero na frente dos dois:

 printf "Hex: %02X\n" 15 

imprimindo um valor hexadecimal em maiúsculas em um campo de 2 caracteres preenchido com zeros

O especificador de precisão permite definir o número de pontos decimais a serem incluídos na saída.

 printf "Ponto flutuante: %08.3f\n" 9.243546 

Usando modificadores de largura e precisão com um número de ponto flutuante

Isso facilita a produção de tabelas de resultados com saída bem alinhada. Este próximo comando também demonstra outra das peculiaridades do Bash printf . Se houver mais argumentos do que especificadores de formato, os argumentos serão alimentados na string de formato em lotes até que todos os argumentos tenham sido usados. O tamanho do lote processado por vez é o número de especificadores de formato na string de formato. Em C, argumentos extras em chamadas de função printf são ignorados.

 printf "Float: %8.3f\n" 9.243546 23.665 8.0021 

Usando modificadores de largura e precisão para criar uma tabela organizada

Você também pode usar os especificadores de largura e precisão com strings. Este comando imprime as strings em um campo de 10 caracteres.

 printf "%10s %d\n" "casacos" 7 "sapatos" 22 "guarda-chuvas" 3 

Usando o modificador de largura com strings

Por padrão, os valores são justificados à direita em seus campos. Para justificá-los à esquerda, use um sinal de menos “ - ” imediatamente atrás do sinal de porcentagem “ % ”.

 printf "%-10s %d" "casacos" 7 "sapatos" 22 "guarda-chuvas" 3 

Usando um especificador de largura justificado à esquerda com strings

O especificador de precisão pode ser usado para definir o número máximo de caracteres que são impressos. Estamos usando os caracteres de dois pontos “ : ” para mostrar os limites do campo de largura. Não como a palavra “guarda-chuvas” é truncada.

 printf ":%10.6s:\n" "casacos" "sapatos" "guarda-chuvas"
 printf ":%-10.6s:\n" "casacos" "sapatos" "guarda-chuvas" 

Usando o modificador de precisão para limitar o número de caracteres que são impressos de uma string

O especificador de largura pode até ser passado como um argumento . Use um asterisco “ * ” em vez de um especificador numérico e passe a largura como um argumento inteiro.

 printf "%*s\n" 20 "Mais à direita" 12 "Médio" 5 "mais à esquerda" 

Passando o especificador de largura como um argumento para printf

Outros truques e curiosidades

Os especificadores de formato dentro da string de formato funcionarão com valores do tipo apropriado, sejam eles fornecidos na linha de comando como argumentos regulares ou sejam gerados como a saída de uma expressão .

Isso imprime a soma de dois números:

 printf "23+32=%d\n" $((23+32)) 

Imprimindo a soma de dois números

Este comando imprime o número de diretórios no diretório de trabalho atual:

 printf "Existem %d diretórios\n" $(ls -d */ | wc -l) 

Contando diretórios com printf

Este comando printf imprime uma string retornada de uma chamada para outro comando.

 printf "Usuário atual: %s\n" $(whoami) 

Imprimindo a saída de outro comando

Se um especificador de formato de string “ %s ” não for fornecido com um argumento, printf não imprime nada.

 printf "Um: %s dois: %s\n" "Alfa" 

Como printf lida com argumentos de string ausentes

Se um especificador de formato de string “ %s ” for fornecido com um valor numérico por engano, ele o imprime como se fosse uma string e não reclama. Não tente isso com o C printf — coisas muito ruins acontecerão. Seu programa provavelmente irá travar. Mas o printf do Bash lida com isso sem reclamar.

 printf "Um: %s dois: %s\n" "Alfa" 777 

Como printf aceita silenciosamente inteiros como valores de string

Se um especificador de formato inteiro “ %d ” não receber nenhum argumento, ele imprimirá zero.

 printf "Inteiro: %d\n" 

Como printf lida com argumentos inteiros ausentes

Se um especificador de formato inteiro “ %d ” receber um argumento de string por engano, o Bash imprimirá uma mensagem de erro e printf imprimirá zero.

 printf "Inteiro: %d\n" "Sete" 

Como printf trata strings que são fornecidas em vez de argumentos inteiros

Símbolos estranhos podem ser gerados usando seu número Unicode ou “ponto de código”. Eles são escapados usando a letra “u” seguida de seu valor Unicode.

 printf "O símbolo do Euro: \u20AC\n" 

Imprimindo um valor Unicode com escape

Para incluir seqüências de escape em strings de argumentos , você deve usar o especificador de formato “ %b ” na string de formato, não o especificador de formato de string “ %s ”.

 printf "%s" "\u20AC\n"
 printf "%b" "\u20AC\n" 

Usando o especificador de formato %b para lidar com sequências de escape em argumentos de string

A primeira instrução printf não processa o valor Unicode e não reconhece a sequência de escape de nova linha. A segunda instrução printf usa o especificador de formato “ %b ”. Isso manipula corretamente o caractere Unicode e uma nova linha é impressa.

RELACIONADO: O que são codificações de caracteres como ANSI e Unicode e como elas diferem?

Cavalos para cursos

Às vezes, tudo o que você precisa fazer é echo algum texto na janela do terminal. Mas quando você precisa aplicar algum posicionamento e formatação, printf é a ferramenta certa para o trabalho.

 printf "%b" "Tha-" "tha-" "tha-" "isso é tudo pessoal.\n"