Excluir linha especifica no txt Topic is solved

Tire suas dúvidas sobre programação em AutoHotkey

Moderator: Gio

thalesduarte
Posts: 95
Joined: 13 Sep 2021, 06:08

Excluir linha especifica no txt

15 Sep 2022, 14:49

Olá, boa tarde.

Como posso fazer para excluir uma linha especifica do txt?


Exemplo, tenho a linha 47 do meu bloco de notas, e gostaria de excluir ela por meio do AHK.




Fiz de uma maneira bem gambiarrada, porém gostaria de saber se há outra maneira melhor.

Segue exemplo:

Code: Select all

Loop, Read, %PastadoArquivoCSV%/parameters.dll ; #JATO
{
if (A_Index = 0)
{
return
}
if (IDDoParametro = A_Index)
{

StringReplace, NovoTexto, A_LoopReadLine, %A_LoopReadLine%, , All
ParametrosGerados := ParametrosGerados NovoTexto "`n"
}
else
{
ParametrosGerados := ParametrosGerados A_LoopReadLine "`n"
}

}

file := FileOpen(PastadoArquivoCSV "/parameters.dll", "w")
file.write(text ParametrosGerados ) 
file.Close()
Basicamente, o código faz uma substituição da linha q eu quero pra um valor em branco.
Sei que não é a forma mais eficiente, existe outra maneira melhor?


Grato pela atenção!
sofista
Posts: 650
Joined: 24 Feb 2020, 13:59
Location: Buenos Aires

Re: Excluir linha especifica no txt

16 Sep 2022, 09:44

Olá: Poderia ser feito com RegEx. Presumo que não haja problemas com a leitura e a escrita de dados, portanto, pulo essas partes. Assumo também que o arquivo inteiro está nos dados variáveis, lido com FileRead, data, <Filename>. Exemplo:

Code: Select all

data := "
(
1
2
3
4
5
6
7
8
9
10
)"

lin := 7    ; Ajuste o número da linha -> 47
MsgBox, % RegExReplace(data, "`am)((^.+?\R){" lin - 1 "})^.+?(.*)", "$1$3")

/* Output:

1
2
3
4
5
6

8
9
10

 */
User avatar
Gio
Posts: 1247
Joined: 30 Sep 2013, 10:54
Location: Brazil

Re: Excluir linha especifica no txt  Topic is solved

16 Sep 2022, 10:07

Bom dia a todos.

Não chamaria seu código de "gambiarra" Thalesduarte. Pra mim não existe essa estória de "código mais certo" se os dois funcionam. A única situação em que isso pode existir é se você estiver buscando algum tipo de otimização (rapidez de execução, menor uso de memória ou algo assim), do contrário se a lógica estiver perfeita, está valendo igualmente pra mim.

De qualquer forma, encontrei um código de RegEx escrito pelo usuário Jeeswg que faz o que você busca. Ele apaga a linha inteira, inclusive os linefeeds:

Code: Select all

TEXTO =
(
primera
segunda
terceira
quarta
quinta
sexta
setima
oitava
nona
decima
)

LINHA_PARA_EXCLUIR := 5 ; Escreva aqui o número da linha que deseja excluir. Se for 5, vai apagar a linha "quinta", removendo também o linefeed dela.

msgbox % RegExReplace(TEXTO, "`n)^(.*`n){" . (LINHA_PARA_EXCLUIR - 1) . "}\K.*`n|$", "") ; Este é o RegEx que apaga a linha desejada

:arrow: OBS: o código acima funciona para todas as linhas, EXCETO a última. Mas é relativamente fácil condicionar isso em uma função se precisar (exemplo: se a linha inserida for igual ao total de linhas do arquivo obtido por um stringsplit em `n, então ao invés de executar o regex acima simplesmente buscaria a última posição de `n e apagaria tudo à direita dali).


@sofista , obrigado pelo código, mas encontrei alguns erros nele e achei válido relatar:
1. Ele parece estar apaganado todas as linhas cujo número seja um múltiplo da linha (por exemplo, se colocar linha 2, ele apaga a 2, 4, 6, 8 e 10.
2. Ele parece estar apagando apenas o primeiro caractere da linha
3. Ele está mantendo os linefeeds das linhas apagadas (causando "buracos" no texto).
sofista
Posts: 650
Joined: 24 Feb 2020, 13:59
Location: Buenos Aires

Re: Excluir linha especifica no txt

16 Sep 2022, 11:39

Olá @Gio: Muito obrigado por se darem ao trabalho de testar o código e minhas desculpas pelos erros. Eles já estão corrigidos.

Com relação ao terceiro ponto, entendi que a OP quer substituir uma linha por um valor em branco. Se devido a questões linguísticas eu não entendi bem e ele não quer isso, então a expressão de substituição é $1$3, ou seja, a linha de alimentação `n é removida.

Code: Select all

data := "
(
primera
segunda
terceira
quarta
quinta
sexta
setima
oitava
nona
decima
)"

lin := 2    ; Ajuste o número da linha -> 47
MsgBox, % RegExReplace(data, "`am)((^.+\R){" lin - 1 "})^.+?\R(.*)$", "$1$3",,1)

/* Output:

primera
terceira
quarta
quinta
sexta
setima
oitava
nona
decima
 */
Editado: removi a linha em branco a pedido de @thalesduarte
Last edited by sofista on 16 Sep 2022, 12:00, edited 1 time in total.
thalesduarte
Posts: 95
Joined: 13 Sep 2021, 06:08

Re: Excluir linha especifica no txt

16 Sep 2022, 11:51

Agradeço ao apoio de todos.

O que estou buscando é excluir uma linha do txt mesmo.

Porém até o momento só consegui fazer, "reescrever a linha, apagando o seu conteúdo".


O ideal pra mim seria que não ficasse esse espaçamento em branco.
Porém, foi a única maneira que consegui =S


Atenciosamente,
Thales
sofista
Posts: 650
Joined: 24 Feb 2020, 13:59
Location: Buenos Aires

Re: Excluir linha especifica no txt

16 Sep 2022, 12:03

@thalesduarte Sem problemas, eu já editei minha última mensagem e removi a linha em branco.

Se me permitem, eu poderia sugerir uma abordagem alternativa. Consiste em utilizar uma matriz simples para ordenar o texto e o método RemoveAt() para remover a linha.

Code: Select all

data := "
(
primera
segunda
terceira
quarta
quinta
sexta
setima
oitava
nona
decima
)"

lin := 2
(arr := StrSplit(data, "`n")).RemoveAt(lin)
; (arr := StrSplit(data, "`r`n")).RemoveAt(lin)    ; "n" é substituído por `r`n" se o texto for lido com FileRead
For k, v in arr
	output .= v "`n"

MsgBox, % output

/* Output:

primera
terceira
quarta
quinta
sexta
setima
oitava
nona
decima

 */
User avatar
Gio
Posts: 1247
Joined: 30 Sep 2013, 10:54
Location: Brazil

Re: Excluir linha especifica no txt

16 Sep 2022, 12:08

sofista wrote:
16 Sep 2022, 11:39
@sofista excelente, obrigado pelo novo código. Testei e de fato ele agora funciona sem os erros relatados, mas assim como o do Jesswg ele também não consegue remover a última linha. Mas gostei muito da opção de alterar o comportamente de "em branco" para "remover a linha" facilmente.

:arrow: Decidi adicionar aquela condicional que comentei para lidar com a opção de remover a última linha. Usei o código do sofista para resolver as linhas anteriores à última pois ele tem a vantagem de trocar facilmente de "remover linha" para "colocar em branco". Ficou assim:

Code: Select all

TEXTO =
(
primera
segunda
terceira
quarta
quinta
sexta
setima
oitava
nona
decima
)

LINHA_PARA_EXCLUIR := 10 ; Escreva aqui o número da linha que deseja excluir
% ((LINHA_PARA_EXCLUIR = strsplit(TEXTO, "`n").MaxIndex()) ? (NOVO_TEXTO :=RegExReplace(TEXTO, "(.*)`n.*", "$1")) : (NOVO_TEXTO := RegExReplace(TEXTO, "`am)((^.+\R){" LINHA_PARA_EXCLUIR - 1 "})^.+?\R(.*)$", "$1$3",,1)))
msgbox % NOVO_TEXTO

sofista wrote:
16 Sep 2022, 12:03

Excelente. Este novo código com matriz funciona inclusive para a última linha também.
sofista
Posts: 650
Joined: 24 Feb 2020, 13:59
Location: Buenos Aires

Re: Excluir linha especifica no txt

16 Sep 2022, 12:38

@Gio Eu adaptei a expressão regular e agora a última linha também pode ser apagada. Para fins de teste, um loop pode ser usado para verificar se cada linha é excluída uma após a outra.

Code: Select all

data := "
(
primera
segunda
terceira
quarta
quinta
sexta
setima
oitava
nona
decima
)"

Loop, 10 {
	lin := A_Index
	MsgBox, % RegExReplace(data, "`am)((^.+\R){" lin - 1 "})(?:^.+\R?(.*)?$)", "$1$3",,1)
}
User avatar
Gio
Posts: 1247
Joined: 30 Sep 2013, 10:54
Location: Brazil

Re: Excluir linha especifica no txt

16 Sep 2022, 12:45

sofista wrote:
16 Sep 2022, 12:38
Agora ficou perfeito :thumbup:
sofista
Posts: 650
Joined: 24 Feb 2020, 13:59
Location: Buenos Aires

Re: Excluir linha especifica no txt

16 Sep 2022, 14:01

Portanto, missão cumprida :D

Saudações

Return to “Ajuda e Suporte Geral”

Who is online

Users browsing this forum: No registered users and 12 guests