Como posso obter o último número de linha de comandos exclusivos ao usar o meu arquivo de histórico?

2

Eu confio no meu arquivo de histórico para comandos anteriores, especialmente aqueles que são longos com muitos parâmetros. Quando eu encontrar o comando e seu número de linha ( nn ) eu uso !nn para executá-lo. Eu prefiro ver a saída completa da pesquisa em vez de fazer uma pesquisa reversa em linha.

Para fazer isso, pesquisei com history | grep some_text

No entanto, tenho a tendência de obter muitos resultados devido a entradas duplicadas (diferindo apenas nos seus números de linha). À medida que minha história cresce, isso piora com o tempo.

Como eu poderia obter uma lista dos comandos exclusivos que eu poderia usar com o operador de comando ! recall?

Eu tentei a história | uniq | grep some_text mas isso não funciona por causa dos números de linha.

Eu posso fazer history | cut -b8- | uniq e isso mostra apenas os comandos.
No entanto, quando eu adiciono sort , recebo $ history | sort sort: string comparison failed: Illegal byte sequence sort: Set LC_ALL='C' to work around the problem. sort: The strings compared were 5359 \ 253 'e 5360 x'.
Além disso, os números de linha desapareceram, o que eu realmente quero para o comando !line-number

Idealmente, eu gostaria que isso acontecesse toda vez que eu fizesse meu history | grep - o que eu faço é um alias hg='history | grep ' , então eu poderia adicionar qualquer solução para isso.

Menos ideal, mas ainda interessante seria a capacidade de executar um programa ad-hoc que tornaria as entradas do arquivo de histórico únicas (novamente, lidando com a questão dos números de linha) para que apenas o comando de histórico mais recente de qualquer dado comando é retido). presumivelmente, excluindo as outras linhas. Mas excluir linhas no arquivo de histórico dessa maneira atrapalha a forma como o arquivo é usado pelo sistema?

    
por Michael Durrant 07.04.2014 / 15:09

3 respostas

2

Você pode dizer:

history | awk '{$1=""; sub("^ ", "", $0)}1' | sort -u

para obter uma lista de entradas exclusivas no history .

No entanto, você também pode definir HISTCONTROL para evitar duplicatas no history :

HISTCONTROL=ignoredups:erasedups

Citações do manual :

HISTCONTROL

A colon-separated list of values controlling how commands are saved on the history list. If the list of values includes ‘ignorespace’, lines which begin with a space character are not saved in the history list. A value of ‘ignoredups’ causes lines which match the previous history entry to not be saved. A value of ‘ignoreboth’ is shorthand for ‘ignorespace’ and ‘ignoredups’. A value of ‘erasedups’ causes all previous lines matching the current line to be removed from the history list before that line is saved. Any value not in the above list is ignored. If HISTCONTROL is unset, or does not include a valid value, all lines read by the shell parser are saved on the history list, subject to the value of HISTIGNORE. The second and subsequent lines of a multi-line compound command are not tested, and are added to the history regardless of the value of HISTCONTROL.

    
por 07.04.2014 / 15:19
0

Você pode analisar o arquivo .bash_history , em vez de usar o comando history . Aqui está um exemplo em awk :

awk '!x[$0]++' .bash_history | nl

Mas como a resposta do @ devnull, você deve usar HISTCONTROL para evitar o comando duplicado e também o comando que começa com spaces :

HISTCONTROL=ignoreboth
    
por 07.04.2014 / 15:47
0

no meu sistema, uniq tem a opção de pular campos.

history | uniq -f 1

me fornece uma listagem exclusiva do meu histórico com números de linha

minha versão:

uniq (GNU coreutils) 8.15

No entanto, isso apenas omite as duplicatas simultâneas, então eu classificaria a saída do histórico, então uniq it:

history | sort -k 2 | uniq -f 1 | sort -n

A última classificação, opcional, reordena as entradas únicas classificadas pelo número do comando

    
por 07.04.2014 / 15:57