Página 1 de 1
Arquivo TXT
Enviado: 19 Fev 2008 14:13
por Valentim
Como posso remover determinadas linhas de um arquivo de LOG e escrever um novo arquivo .txt?
Por exemplo:
Código: Selecionar todos
Linha 01: RCS file: /cvs/1.fmb,v
Linha 02: head: 1.5
Linha 03: locks: strict
Linha 04: total revisions: 6; selected revisions: 1
Linha 05: description:
Quero escrever o novo arquivo .txt com as seguintes linhas 02 e 04 e apagar as outras linhas sem deixar espaços em branco.
se alguem puder ajudar...
Muito Obrigado
Enviado: 19 Fev 2008 14:19
por Maligno
Seja bem-vindo ao fórum.
Se sua dúvida é com relação ao melhor tipo de procedimento:
Acho que a melhor alternativa, que eu adotaria, aliás, é renomear o arquivo original, ler este arquivo linha a linha, e gravar no arquivo destino apenas as que desejar salvar.
Se sua dúvida é com relação à técnica dentro do conceito da linguagem:
Eu sempre prefido utilizar as funções de manipulação de arquivo em baixo nível: FCreate(), FOpen(), etc. Me sinto mais à vontade com elas. Até porque, com elas a performance é melhor. Mas você também poderia utilizar as funções MemoRead() e MemoWrite() (nunca usei). Mas ainda assim você terá que separar as linhas.
Se não consegui esclarecer muita coisa, especifique melhor qual é sua dúvida.
Enviado: 19 Fev 2008 14:25
por Valentim
Obrigado Maligno,
Sou meio novato na linguagem Clipper, tentei fazer esse programinha mais pra facilitar a minha vida, pois estou precisando editar um arquivo com mais de 5 mil linhas e capturar somente essas linhas que informei.
No Programa que estou tentando fazer a duvida e como buscar as linhas que que quero OU como apagar as linhas que não quero....
Enviado: 19 Fev 2008 14:29
por Maligno
Esse assunto já foi discutido algumas vezes. Certa vez postei um código simples, para efeito de exemplo. Acho que ele pode ajudá-lo a ter um ponto de partida.
Código: Selecionar todos
#define _kSIZE 16*1024
#define _kEOL Chr(13)+Chr(10)
//------------------------------------------------------------
function Leitura(cFileN)
local nByts // bytes lidos na iteração
local nLins := 0 // quantidade de linhas
local cBuff := Space(_kSIZE) // buffer de armazenamento
local cRest := "" // resto da leitura
local cFileH := FOpen(cFileN)) = -1 // alça do arquivo aberto
*
if nFileH = -1
// Erro na abertura do arquivo! Trate o erro à sua maneira
return .F.
end
*
while (nByts := FRead(cFileH,@cBuff,_kSIZE)) > 0 .or. !Empty(cRest)
cBuff := RTrim(cBuff)
cBuff := cRest+cBuff
cBuff += if(nByts=0 .and. Right(cBuff,2) != _kEOL, _kEOL, "")
//
// Individualização da linha através do par CR/LF (_kEOL)
while (i := At(_kEOL,cBuff)) > 0
// A linha já individualizada, sem _kEOL
cLine := Left(cBuff,i-1)
// Ajuste do buffer, descartando o _kEOL
cBuff := SubStr(cBuff,i+2)
// Contador de linhas, caso precise
nLins ++
//
//
// Neste ponto você poderá fazer sua pesquisa
// dentro da linha, usando as funções básicas
// do Clipper.
//
//
end
// Pode sobrar algo após o último _kEOL
cRest := cBuff
// Reset do buffer para nova leitura
cBuff := Space(_kSIZE)
end
return .T.
Preparei para ele "puxar" 16KB de vez. Note que o Clipper tem um limite de 64KB. Mas se precisar, mude a constante _kSIZE para o tamanho que achar mais apropriado, até o limite do Clipper.
Enviado: 19 Fev 2008 14:35
por Valentim
Não entendi completamente o código passado, só estou tentando encontrar um conjunto de caracteres em uma string para cada linha do arquivo, para apagar a linha OU gravar a mesma em outro arquivo.
Mas mesmo assim vou tentar utilizar algumas coisas para ver se consigo algo.
Obrigado
Enviado: 19 Fev 2008 14:42
por Maligno
O código não é tão difícil de entender quanto parece. Ele abre o arquivo origem e carrega pedaços dele para a memória. Esse buffer é trabalhado dentro da malha WHILE, para que sejam separadas as linhas, que a partir daí poderão ser analisadas separadamente.
Há diversas formas de fazer o que você quer. Essa é apenas uma delas.

Enviado: 19 Fev 2008 15:24
por Valentim
Cheguei até a utilizar o SDF pra passar o arquivo TXT pra DBF mais ta complicado escrever o novo arquivo com as linhas corretas
meu programinha aqui ta uma loucura, nem eu to entendendo mais o que tou fazendo
Enviado: 19 Fev 2008 17:19
por Pablo César
Valentim escreveu:Cheguei até a utilizar o SDF pra passar o arquivo TXT pra DBF
O que não estaria errado. O exemplo dado pelo Maligno é feito diretamente no arquivo TXT em baixo nível (é correto também).
Se você ainda tiver o procedimento que importa o TXT para o DBF você poderá tratar (isto é eliminar as linhas) no DBF mesmo. Você tem alguma referência que queira mencionar para tê-la como condição ?. Ou seria conviente apresentar na tela e apagar manualmente ou até selecionar as linhas que deseja apagar. Se for isto que precisa, é só exibí-las num TBROWSE. Uma vez que você selecionou o que tem que ser deletado é só deletar e gerar o arquivo (com o mesmo nome), mas tem que ter certeza que o SET DELETED esteja ON
Obs.: Se este arquivo de LG está numa rede, você precisará fazer um semáforo que nesse momento de apagar as linhas do LOG, ninguém possa a vir a gravar, porque senão vai se perder nessa "manutenção".
Enviado: 19 Fev 2008 17:52
por Valentim
Estou quase conseguindo utilizando o SDF e a função AT do Clipper, porém ainda estou aperfeiçoando... caso eu não consiga completar volto aqui novamente para tirar mais algumas duvidas

Enviado: 20 Fev 2008 08:55
por Valentim
1. Pronto, consegui fazer uma parte utilizando o seguinte código...
Código: Selecionar todos
cRCS := cRev := cDtAu := cDesc := ""
cArqTmp := "CVS"
aTemp := {}
Aadd (aTemp, {"TEXTO","C",300,0})
DBCreate (cArqTmp, aTemp)
DBUseArea ( .t.,,cArqTmp,, .f., .f.)
Append From log_cvs.txt SDF
SET PRINTER ON
SET DEVICE TO PRINTER
SET PRINTER TO LogCVS.txt
SET CONSOLE OFF
SET CURSOR OFF
DBGoTop()
Do While !Eof()
cLoc1 := "RCS file: "
nPosIni1 := AT(cLoc1,TEXTO)
nPosFim1 := AT(",v",SubStr(TEXTO,nPosIni1,Len(TEXTO)))
if nPosFim1 > 0
cRCS := SubStr(TEXTO,nPosIni1,nPosFim1-nPosIni1)
@ PROW() + 00,00 SAY cRCS
endif
cLoc2 := "revision "
nPosIni2 := AT(cLoc2,TEXTO)
nPosFim2 := AT("revision ",SubStr(TEXTO,nPosIni2,Len(TEXTO)))
if nPosFim2 > 0
cRev := SubStr(TEXTO,nPosIni2,(nPosFim2+20)-nPosIni2)
@ PROW() + 01,00 SAY cRev
endif
cLoc3 := "date: "
nPosIni3 := AT(cLoc3,TEXTO)
nPosFim3 := AT("; state: ",SubStr(TEXTO,nPosIni3,Len(TEXTO)))
if nPosFim3 > 0
cDtAu := SubStr(TEXTO,nPosIni3,(nPosFim3+1)-nPosIni3)
@ PROW() + 01,00 SAY cDtAu
@ PROW() + 01,00 SAY Replicate('=',77)
@ PROW() + 01,00 SAY ""
endif
DBSkip()
EndDo
2. Porém está faltando a parte da "
descrição", vou mostrar um exemplo completo do arquivo de leitura...
Código: Selecionar todos
RCS file: /u01/cvs/rps-v48/acma/M_SOLICITACAO_SERV.fmb,v
Working file: M_SOLICITACAO_SERV.fmb
head: 1.20
branch:
locks: strict
access list:
keyword substitution: b
total revisions: 28; selected revisions: 1
description:
----------------------------
revision 1.17
date: 2007/09/14 18:36:48; author: author001; state: Exp; lines: +354 -296
/*
PDA 201138 - 14/09/2007 - D.F.N.
DESCRIÇÃO: Na Trigger WHEN-VALIDATE-ITEM do campo CD_BEM e DSP_DS_PLAQUETA, alterada a consulta, pois não trazia
o código do Setor
*/
=============================================================================
RCS file: /u01/cvs/rps-v48/acma/M_TIPO_OS.fmb,v
Working file: M_TIPO_OS.fmb
head: 1.8
branch:
locks: strict
access list:
keyword substitution: b
total revisions: 9; selected revisions: 1
description:
----------------------------
revision 1.6
date: 2007/04/13 18:26:24; author: author002; state: Exp; lines: +142 -206
recompilacao
=============================================================================
RCS file: /u01/cvs/rps-v48/acma/R_ABERTURAOS.rdf,v
Working file: R_ABERTURAOS.rdf
head: 1.6
branch:
locks: strict
access list:
keyword substitution: b
total revisions: 9; selected revisions: 1
description:
----------------------------
revision 1.6
date: 2007/04/29 19:05:11; author: author003; state: Exp; lines: +3965 -1612
PDA 178252
Substituida a trigger after repport pela formula CF_ATUALIZAOSIMPRESSA
=============================================================================
3. A "Descrição" seria todos o texto abaixo da linha onde é informado "
Date", "
Author", "
State" e "
Lines" até a linha ======
4. O Resultado está da seguinte maneira (Sem a "
Descrição" que é fundamental)
Código: Selecionar todos
RCS file: /u01/cvs/rps-v48/acma/M_SOLICITACAO_SERV.fmb,v
revision 1.17
date: 2007/09/14 18:36:48; author: author001;
=============================================================================
RCS file: /u01/cvs/rps-v48/acma/M_TIPO_OS.fmb,v
revision 1.6
date: 2007/04/13 18:26:24; author: author002;
=============================================================================
RCS file: /u01/cvs/rps-v48/acma/R_ABERTURAOS.rdf,v
revision 1.6
date: 2007/04/29 19:05:11; author: author003;
=============================================================================
Alguém teria alguma idéia de como fazer para capturar a
Descrição...
Enviado: 20 Fev 2008 11:22
por Maligno
Repare que o que você quer é a linha que inicia com RCS, a linha que inicia com revisision e a linha que inicia com date. Essas são suas pistas. Uma vez que todas as linhas estão devidamente separadas, basta analisar cada linha em busca dessas strings chave.
Enviado: 20 Fev 2008 14:30
por Valentim
Exatamente, o meu problema está sendo capturar vários registros do dbf...
por exemplo, capturar o registro 11 até 16
Código: Selecionar todos
Registro XX: AAAAAAAAAAAAAAAAAAAAAAA
Registro 11: /*
Registro 12: PDA 201138 - 14/09/2007 - D.F.N.
Registro 13: DESCRIÇÃO: Na Trigger WHEN-VALIDATE-ITEM do campo CD_BEM e Registro 14: DSP_DS_PLAQUETA, alterada a consulta, pois não trazia
Registro 15: o código do Setor
Registro 16: */
Registro XX: AAAAAAAAAAAAAAAAAAAAAAAA
qual a "pista" para ele capturar esses registros se eles podem ser completamentes diferentes?

escolher alguns poucos registros em sequencia ascendente
Enviado: 02 Mar 2008 21:38
por Manuel Luis Modernel
OI Valentim,
Uns 13 anos atras fiz alguma coisa em Clipper Summer 87, não sei se entendi teu problema mais eu fazia assim:
Indexava o DBF por item (se necessário colocava mais um campo numerico indicando no teu casso os numeros dos campos 11 a 16, dai com um Seek ia até o nº 11 e com varios Skeep num While - Loop chegava até registro nº 16 depois saia do dbf.
Coloquei ai uma pergunta, ve se consegue me ajudar, como leer um arquivo txt de dentro do Clipper.