Mostrando postagens com marcador mv. Mostrar todas as postagens
Mostrando postagens com marcador mv. Mostrar todas as postagens

quarta-feira, 21 de dezembro de 2011

Soma dos débitos do extrato do Banco do Brasil

  Eu sempre fiz o controle dos meus gastos e para ter a resposta do custo do mês, desenvolvi um script que soma todas as parcelas debitadas da minha conta corrente do banco do Brasil.
  Começou de uma forma bem simples. Um conjunto de entradas e saídas era sequênciado da seguinte forma:
  • o comando cat exibe todo o conteúdo
  • o comando cut mostrar do caracter 60 em diante
  • o grep exibe somente as linhas de débito (indicadas por um "D")
  • o awk exibe somente o primeiro campo da linha de débito
  • o comando sed substitui vírgula por ponto
  • o paste e suas opções transformam a listagem de coluna para linha e insere um sinal de mais (+) entre os números
  • o comando bc faz a soma
Observação: a necessidade de substituir a vírgula por ponto é devido ao bc requerer este símbolo para interpretar valores fracionários.

  Até Maio de 2007 e anterior a esta data, o comando era:

cat extrato_07_05.txt | cut -c 60- | grep D | awk '{printf("%s\n",$1)}' | sed 's/,/./g' | paste -s -d"+" | bc

  De Junho de 2007 até o presente, usa-se:

cat extrato_07_06.txt | cut -c 71- | grep D | awk '{printf("%s\n",$1)}' | sed 's/,/./g' | paste -s -d"+" | bc

  Estes comandos combinados funcionavam para valores até 999 reais. A partir dos valores contendo 4 dígitos, este é exibido com um ponto separador de milhar. Exemplo: 1.000,00   Como consequência, causa um erro no interpretador do bc. Para resolver o problema, apresento a solução abaixo bem como os comentários.

#!/bin/bash
# Variáveis mes e ano capturam a data
mes=`date +%m`
ano=`date +%Y`

# Exige o número do arquivo ao executar o comando
 if [ $# != 1 ]
   then
    echo "Argumento: nome_de_arquivo"
    exit 1
  fi

cat $1 | cut -c 71- | grep D | awk '{printf("%s\n",$1)}' | sed 's/,/./g' > extrato.txt
# Conta a quantidade de linhas ao ler o arquivo
total_linhas=`wc -l extrato.txt | cut -f1 -d" "`
# Apaga o arquivo
rm -f gasto_"$ano"_$mes.txt
# Loop para executar um conjunto de ações até o final do arquivo
for i in `seq $total_linhas`
  do
# Analisa cada linha e conta o número de pontos (separadores de milhar e da parte fracionária)
   um_ponto=`head -n $i extrato.txt | tail -n 1 | tr -cd "." | wc -c`
   if [ $um_ponto = 1 ]
    then
# Se for apenas 1 ponto, simplesmente exibe o valor
    head -n $i extrato.txt | tail -n 1
   fi

# Analisa cada linha e conta o número de pontos (separadores de milhar e da parte fracionária)
  dois_pontos=`head -n $i extrato.txt | tail -n 1 | tr -cd "." | wc -c`
   if [ $dois_pontos = 2 ]
    then
# Se forem 2 pontos, substitui o primeiro ponto por nada (ponto aparece somente para parte fracionária)
    echo `head -n $i extrato.txt | tail -n 1` | sed 's/\.//'
   fi
  done >> gasto_"$ano"_$mes.txt
paste -s -d"+" gasto_"$ano"_$mes.txt | bc

sábado, 17 de setembro de 2011

Criando páginas rápidas com fotos

  O propósito deste script é gerar uma página para cada foto. Cada página tem dois links sendo o anterior e a próxima (exceção para a primeira e a última). Em outras palavras, aparecerá um número em ordem crescente(iniciado em 1) para cada foto, a foto e os links entre as páginas adjacentes.
  Esta necessidade surgiu para eu mostrar para os meus pais que tem dificuldade de lidar com o computador. Então juntei alguns conhecimentos para facilitar para eles. Recomendo redimensionar as fotos para não demorar no carregamento (veja Convertendo as fotos de um diretório específico ).
  O script exige que as fotos estejam numeradas sequencialmente. Para automatizar esta etapa, junte com o script que está em Renomear de maiúscula para minúscula e com sequência numérica . Copie e execute o segundo script desta página.
  As últimas instruções do script são 4 ajustes:
  • Trocar o link de número 010 por 10
  • Trocar o link de número 9 por 09
  • Eliminar da primeira página o link para página anterior
  • Eliminar da última página o link para a página seguinte
  Para entender como os arquivos TXT criaram os arquivos HTML, recomendo a leitura Marcas do Txt2tags do genial Aurélio Marinho Jargas.
  Depois de executar o script abaixo, transfira para o seu servidor web as fotos e os arquivos HTML. Uma alternativa que requer um pouco mais de conhecimento é configurar o Apache e o seu roteador para fazer um port forwarding. Assim, meus pais acessavam as fotos diretamente do meu computador.

#/bin/bash

# v1.1 September, 11th, 2010

total=`ls *.jpg | wc -l`
for i in `seq 9`
  do
   let j=$i-1
   let k=$i+1
echo "


=0$i/$total=

[0$i.jpg]


[anterior 0$j.html]


[proxima 0$k.html]
" > 0$i.txt
  done

for i in `seq 10 1 $total`
  do
   let j=$i-1
   let k=$i+1
echo "


=$i/$total=

[$i.jpg]


[anterior $j.html]

[proxima $k.html]
" > $i.txt
  done


# txt2html

for i in $total
  do
   txt2tags -t html *.txt
  done


sed 's/010/10/' 09.html > 09temp
mv -v 09temp 09.html

sed 's/9.html/09.html/' 10.html > 10temp
mv -v 10temp 10.html

sed '/anterior/d' 01.html > primeiroTemp
mv -v primeiroTemp 01.html

sed '/proxima/d' $total.html > ultimoTemp
mv -v ultimoTemp "$total".html

sexta-feira, 5 de agosto de 2011

Renomeando arquivos para o padrão Unix


Muitas vezes recebo arquivos que vem com espaços e parenteses e não é muito conveniente tratá-los no shell. Então eu prefiro eliminar esses caracteres. É o serviço do script abaixo.
Para executar, proceda assim:

./script nome_arquivo

para que o script saiba qual arquivo deve renomear.

Então, a primeira providência é uma checagem se foi passado o argumento através da condição if [ $# != 1 ].
Estando tudo bem, o script começa a renomear. O nome do arquivo fica armazenado na variável $1 e passa a transferir novos valores para as variáveis seguinte que foram usados nomes bem intuitivos.
De com_espaco passa o novo valor para sem_espaco.
sem_espaco para minuscula através do comando tr.
De minuscula para dash que substitui a sequência "_-_" por "-" através do sed.
Do dash para abre_parenteses e em seguida para fecha_parenteses que em ambos os casos usam o sed para substituir os caracteres.




#!/bin/bash
# remove spaces, uppercase to lowercase, replace " - " for "-", replace "(" for "-" and replace ")"for ""

# If file name isn't given show message
if [ $# != 1 ]
  then
   echo "Argumento: nome_de_arquivo"
   exit 1
fi

# grab the file name
com_espaco=`ls -1 "$1"`
# change space for underline
sem_espaco=`ls -1 "$1" | sed 's/ /_/g'`
#echo "$sem_espaco"
mv -v "$com_espaco" "$sem_espaco"
minuscula=$(echo "$sem_espaco" | tr A-Z a-z)
# change upper for lowercase
mv -v "$sem_espaco" "$minuscula"
# change _-_ for -
dash=`echo "$minuscula" | sed 's/_-_/-/'`
mv -v "$minuscula" "$dash"

ls "$dash" | grep "("
if [ $? -eq 0 ]
  then
   abre_parenteses=`ls "$dash" | sed 's/(/-/g'`
   mv -v "$dash" "$abre_parenteses"
fi

ls "$abre_parenteses" | grep ")"
if [ $? -eq 0 ]
  then
   fecha_parenteses=`ls "$abre_parenteses" | sed 's/)//g'`
   mv -v "$abre_parenteses" "$fecha_parenteses"
fi


Podemos automatizar este trabalho se forem muitos arquivos. Se for para os arquivos do mesmo diretório, há uma forma bem simples. Digite a linha de comando no seu terminal:


$ ls -1 | { while read arq; do ./script "$arq"; done; }


Apacerá uma mensagem de erro caso o nome de arquivo não tenha parênteses, mas garanto que no fim tudo estará devidamente renomeado.
É mais ágil quando é dado um duplo clique numa palavra e o terminal seleciona inteira facilitando o trabalho de copiar e colar.

quinta-feira, 4 de agosto de 2011

Numerando arquivos de forma cronológica


Desenvolvi este script para organizar a reunião de fotos de mais de uma máquina digital. Desta forma, independente como as câmera registram o nome de arquivo, as fotos são renomeadas de acordo com a sequência cronológica.
Primeiro, os nomes são renomeados para maiúsculas como foi no post Renomear de maiúscula para minúscula e com sequência numérica .

O comando ls -1 *.jpg trata de colunar todos os arquivos com essa extensão e a cada linha que avança, as variáveis ano, mes, dia, hora, mim, seg recebem seus respectivos valores e o comando tee -a faz duas tarefas:
  • exibe a saída na tela
  • armazena a saída no arquivo foto.txt
Como extrair a informação através do exiftool demanda processamento e dependendo da quantidade parece travado, exibir as mensagens mostra que o programa está executando. O passo seguinte é contar a quantidade de arquivos jpg e armazenar na variável total. Essa informação é usada no laço for para ser o critério de parada. Neste exemplo, fiz para mais de 100 fotos para que todos os nomes de arquivos fiquem com três dígitos (001.jpg, 002.jpg, .., 010.jpg, ..., 100.jpg, ...). Fica a seu critério a quantidade de dígitos. Caso opte por não preencher com 0s (zeros), use o exemplo sem dígitos.

#/bin/bash

for M in *.JPG
  do
    m=$(echo $M | tr A-Z a-z)
    mv -v $M $m
done

ls -1 *.jpg | {
  while read arq; do
    ano=`exiftool "$arq" | grep Original | sed 's/://g' | sed 's/ //g' | cut -c 18-21`
    mes=`exiftool "$arq" | grep Original | sed 's/://g' | sed 's/ //g' | cut -c 22-23`
    dia=`exiftool "$arq" | grep Original | sed 's/://g' | sed 's/ //g' | cut -c 24-25`
    hora=`exiftool "$arq" | grep Original | sed 's/://g' | sed 's/ //g' | cut -c 26-27`
    min=`exiftool "$arq" | grep Original | sed 's/://g' | sed 's/ //g' | cut -c 28-29`
    seg=`exiftool "$arq" | grep Original | sed 's/://g' | sed 's/ //g' | cut -c 30-31`
    echo "$arq" $ano$mes$dia$hora$min$seg
done
} | tee -a fotos.txt

cat fotos.txt | awk '{printf "%s %4s\n",$2,$1}' | sort -n > fotos2.txt

total=`ls *.jpg | wc -l`

for i in `seq 9`
  do
    file=`head -n $i fotos2.txt | tail -n 1 | cut -f2 -d ' '`
    mv -v $file 00$i.jpg
  done

for i in `seq 10 1 99`
  do
    file=`head -n $i fotos2.txt | tail -n 1 | cut -f2 -d ' '`
    mv -v $file 0$i.jpg
  done

for i in `seq 100 1 $total`
  do
    file=`head -n $i fotos2.txt | tail -n 1 | cut -f2 -d ' '`
    mv -v $file $i.jpg
  done

Recomendo esta automatição de renomear arquivos de acordo com o data e hora quando várias pessoas participaram da mesma viagem, por exemplo. Assim, a visualização não será exibida em dias alternados. Para encerrar, dois cuidados:

  • Garantir a câmera de todos estejam com a data e hora correta. Não precisam estar sincronizadas, apenas corretas.
  • Difícil acontecer, mas caso exista um arquivo que até foi tirada no mesmo segundo, uma das fotos será sobreescrita.

quarta-feira, 3 de agosto de 2011

Renomeando arquivos com sequência numérica a partir de um valor


O objetivo deste código-fonte é renomear arquivos com uma sequência numérica iniciando a partir de um determinado número. Neste exemplo, começa com o número 196. Executando no diretório que contém os arquivos *.jpg (observe que obedece o critério que está na linha com a variável nome), os novos nomes de arquivos tornam-se:

pag196.jpg, pag197.jpg, pag198.jpg, ...

até o último arquivo jpg que for encontrado.
A variável total conta os arquivos jpg para entregar ao laço for o critério de parada.
A variável nome armazena o nome do arquivo através do laço for que coloca os nomes em uma coluna e vai avançando linha a linha.
O comando mv renomeia cada arquivo.
O comando let incrementa a variável j.


#!/bin/bash

total=`ls *.jpg | wc -l`
j=196;

for i in `seq $total`
 do
   nome=`ls -1 *.jpg | head -n $i | tail -n 1`
   mv -v $nome pag$j.jpg
   let j++;
 done



Uma aplicação recomendada deste script como pode ser visto pelo novo nome de arquivo pag_NUMERO_.jpg é organizar de acordo com as páginas digitalizadas. Ler o documento no formato digital torna extremamente fácil localizar no livro digitalizado bastando apenas ver o nome do arquivo.