Comandos do Pré-processador

O KDiff3 suporta duas opções do pré-processador.

Comando do pré-processador:

Quando for lido qualquer ficheiro, ele será encaminhado através deste comando externo. O resultado deste comando será visível em vez do ficheiro original. O utilizador poderá criar o seu próprio pré-processador que corresponda às suas necessidades específicas. Use isto para cortar partes desnecessárias do ficheiro ou para corrigir automaticamente a indentação, etc.

Comando do Pré-processador para a Correspondência de Linhas:

Quando for lido qualquer ficheiro, ele será encaminhado através deste comando externo. Se um comando de pré-processador (ver acima) for também indicado, então o resultado do pré-processador é a entrada para o pré-processador de correspondência de linhas. O resultado só será usado durante a fase de correspondência de linhas da análise. O utilizador poderá escrever o seu próprio pré-processador que corresponda às suas necessidades específicas. Cada linha de entrada terá de ter uma linha de resultado correspondente.

A ideia é permitir ao utilizador uma maior flexibilidade ao configurar o resultado das diferenças. Mas isto necessita de um programa externo e muitos dos utilizadores não querem escrever um. As boas notícias é que, muitas das vezes, o sed ou o perl encarregar-se-ão disso.

Exemplo: Caso de teste simples. Considere o ficheiro a.txt (6 linhas):

      aa
      ba
      ca
      da
      ea
      fa

E o ficheiro b.txt (3 linhas):

      cg
      dg
      eg

Sem um pré-processador as seguintes linhas teriam sido colocadas lado a lado:

      aa - cg
      ba - dg
      ca - eg
      da
      ea
      fa

Isto provavelmente não será o desejado, dado que a primeira letra contém a informação realmente interessante. Para ajudar o algoritmo de correspondência a ignorar aa segunda letra, poder-se-ia usar um comando de pré-processamento de correspondências de linhas que substituísse o 'g' pelo 'a':

   sed 's/g/a/'

Com este comando, o resultado da comparação seria:

      aa
      ba
      ca - cg
      da - dg
      ea - eg
      fa

Internamente, o algoritmo de correspondência vê os ficheiros depois de correr o pré-processador de correspondência de linhas, mas no ecrã o ficheiro fica inalterado. (O pré-processador normal iria alterar também os dados no ecrã.)

Bases do sed

Esta secção só introduz algumas funcionalidades muito básicas do sed. Para mais informações veja as páginas info:/sed ou http://www.gnu.org/software/sed/manual/html_mono/sed.html. Existe uma versão pré-compilada para o Windows em http://unxutils.sourceforge.net. Repare no facto de que os exemplos seguintes assumem que o comando sed está numa pasta referida pela sua variável de ambiente PATH. Se não for este o caso, você terá de indicar a localização absoluta completa para o comando.

Nota

Lembre-se também que os exemplos seguintes usam a plica simples (') que não irá funcionar no Windows. No Windows, deverá usar as aspas (") em alternativa.

Neste contexto apenas o comando de substituição do sed será usado:

   sed 's/EXPREG/SUBSTITUTO/OPÇÕES'

Antes de você usar um comando novo no KDiff3, deverá primeiro testá-lo numa consola. Aqui, o comando echo é útil. Exemplo:

   echo abracadabra | sed 's/a/o/'
   -> obracadabra

Este exemplo mostra um comando 'sed' muito simples que substitui a primeira ocorrência do "a" por um "o". Se quiser substituir todas as ocorrências, então irá necessitar da opção "g":

   echo abracadabra | sed 's/a/o/g'
   -> obrocodobro

O símbolo "|" é o 'pipe' ou canal que transfere o resultado do comando anterior para os dados de entrada do comando seguinte. Se quiser testar com um ficheiro maior, então poderá usar o cat no sistemas do tipo do Unix ou o type nos sistemas do tipo Windows. O sed irá fazer a substituição para cada linha.

cat ficheiro | sed opções

Exemplos para a Utilização do sed no KDiff3

Ignorar Outros Tipos de Comentários

De momento, o KDiff3 só compreende comentários de C/C++. Se usar o comando "Pré-Processador de Correspondência de Linhas", poderá também ignorar outros tipos de comentários, convertendo-os em comentários de C/C++. Exemplo: Para ignorar comentários que comecem por "#", poderá convertê-los para "//". Lembre-se que terá também de activar a opção "Ignorar os Comentários de C/C++" para obter efeito. Um comando "Pré-Processador de Correspondência de Linhas" seria:

   sed 's/#/\/\//'

Dado que para o sed o carácter / tem um significado especial, é necessário colocar o carácter \ antes de cada / no texto de substituição. Algumas das vezes o \ é necessário para adicionar ou remover um significado especial para certos caracteres. As plicas simples (') antes e depois do comando de substituição são importantes, caso contrário a linha de comandos iria tentar interpretar alguns caracteres especiais como o #, o $ ou o \ antes de os passar para o sed. Lembre-se que no Windows® irá necessitar aqui das aspas ("). O Windows® substitui os outros caracteres como o %, por isso você terá de fazer algumas experiências.

Diff sem Distinguir Capitalização

Use o comando "Pré-Processador de Correspondência de Linhas" para converter todo o texto para maiúsculas:

   sed 's/\(.*\)/\U\1/'

Aqui o .* é uma expressão regular que corresponde a qualquer texto e, no seu contexto, irá corresponder a todos os caracteres da linha. O \1 no texto de substituição refere-se ao texto correspondente ao primeiro par de \( e \). O \U converte o texto inserido para maiúsculas.

Ignorar as Palavras-Chave do Controlo de Versões

O CVS e outros sistemas de controlo de versões usam várias palavras-chave para inserir texto gerado automaticamente (info:/cvs/Keyword substitution). Todas elas seguem o padrão "$PALAVRACHAVE texto gerado$". É preciso agora um comando Pré-Processador de Correspondência de Linhas que remova apenas o texto gerado:

   sed 's/\$\(Revision\|Author\|Log\|Header\|Date\).*\$/\$\1\$/'

O "\|" separa as palavras-chave possíveis. Poderá querer modificar esta lista de acordo com as suas necessidades. O "\" antes do "$" é necessário, caso contrário o "$" irá corresponder ao fim da linha.

Ao experimentar com o sed, você poderá vir a compreender e até a gostar destas expressões regulares. Elas são úteis porque existem muitos outros programas que suportam algumas coisas desse género.

Ignorar os Números

A indiferença em relação aos números é de facto uma opção incorporada. Mas, como outro exemplo, seria assim como iria ficar como um comando do Pré-Processador da Correspondência de Linhas.

   sed 's/[0123456789.-]//g'

Todos os caracteres dentro de '[' e ']' são uma correspondência e será substituído por nada.

Ignorar Certas Colunas

Em algumas ocasiões um determinado texto tem uma formatação demasiado restrita e contém colunas que deseja sempre ignorar, enquanto que existem outras colunas que deseje preservar para análise. No exemplo seguinte, as primeiras cinco colunas (caracteres) são ignoradas, as próximas dez são preservadas, depois as próximas cinco colunas serão ignoradas de novo e o resto da linha é preservada.

   sed 's/.....\(..........\).....\(.*\)/\1\2/'

Cada ponto '.' corresponde a um único carácter. O "\1" e o "\2" no texto de substituição refere-se ao texto correspondente dentro do primeiro e segundo par de "\(" e "\)", demarcando o texto a ser preservado.

Combinar Várias Substituições

Em algumas situações você deseja aplicar várias substituições de uma vez. Poderá então usar o ponto-e-vírgula ";" para separar uma da outra. Exemplo:

echo abracadabra | sed 's/a/o/g;s/\(.*\)/\U\1/'
   -> OBROCODOBRO

Usar o perl em vez do sed

Em vez do sed, você poderá querer usar algo diferente como o perl.

   perl -p -e 's/EXPREG/SUBSTITUTO/OPÇÕES'

Porém, alguns detalhes são diferentes no perl. Repare que, onde o sed necessitava do "\(" e do "\)", o perl necessita dos "(" e ")" mais simples e sem o '\' precedente. Exemplo:

sed 's/\(.*\)/\U\1/'
   perl -p -e 's/(.*)/\U\1/'

Order de Execução de Pré-processadores

Os dados são encaminhados através de todos os pré-processadores internos e externos pela seguinte ordem:

  • Pré-processador normal,

  • Pré-processador de Correspondência de Linhas,

  • Ignorar capitalização (conversão para maiúsculas),

  • Detecção de Comentários de C/C++,

  • Ignorar os números,

  • Ignorar os espaços em branco

Os dados após o pré-processador normal serão preservados para a apresentação e para a junção. As outras operações só modificam os dados que o algoritmo para a correspondência de linhas nas diferenças vê.

Nos casos raros em que você usa um pré-processador normal, repare que o pré-processador da correspondência de linhas vê o resultado no pré-processador normal como dados de entrada.

Aviso

Os comandos do pré-processador são normalmente muito úteis, mas como acontece com qualquer opção que modifica os seus textos ou esconde algumas diferenças automaticamente, você poderá saltar por cima de certas diferenças e, no pior dos casos, destruir dados importantes.

Por esta razão, durante uma junção, se for usado um comando pré-processador normal, o KDiff3 dizer-lhe-á isso e perguntar-lhe-á se deverá ser desactivado ou não. Mas não o irá avisar se estiver um Pré-Processador de Correspondência de Linhas activo. A junção não irá ficar completa até que todos os conflitos tenham sido resolvidos. Se tiver desactivado o "Mostrar os Espaços em Branco", então as diferenças que foram removidas com o Pré-Processador de Correspondência de Linhas ficarão também invisíveis. Se o botão para Gravar continuar inactivo durante uma junção (devido a conflitos por resolver), verifique se activa o "Mostrar os Espaços em Branco". Se não quiser juntar essas diferenças menos importantes poderá escolher a opção "Escolher [A|B|C] nos Conflitos de Espaço em Branco por Resolver" no menu "Juntar".