Resposta curta: o fc
comando de correção) do bash
fc
é o comando, embutido no bash shell, feito para editar & re-execute comandos da história.
É presente no CygWin também e funciona em todas as distribuições do Linux nas quais eu testei:
fc -s '\'='/' -1
Algumas explicações
-
fc
é o bash integrado comando para listar ou editar e reexecutar comandos da lista de histórico.
-
-1
terá o último comando no histórico. Observe que mesmo !!
é definido (lido em man bash
) como
!! Refer to the previous command. This is a synonym for
!-1'.
-
-s
para substituir um padrão por outro. Desta vez, a partir de help fc
(comando interno, então help
):
With the 'fc -s [pat=rep ...] [command]' format, COMMAND is
re-executed after the substitution OLD=NEW is performed.
Ok, eles significam pat=rep
em vez de OLD=NEW
...
- Os padrões serão lidos pelo shell, então temos que protegê-los com aspas:
'\'
e '/'
.
Algumas palavras mais sobre por que você está recebendo "substituição falhou"
Parece que o modificador s
não é (ainda ) implementou a substituição do caractere de barra invertida \
, que é o escape. Para ter certeza, deveríamos ver o código, por exemplo, da versão do gnu da expansão do histórico do bash (mas havia o comando acima para obter o que você estava tentando fazer ... então eu fico com preguiça ....).
Algumas notas:
-
Somos levados a pensar que funcionará cada RegEx que encontramos trabalhando com sed
, mas isso não é garantido. A barra invertida é o caracter de escape da expansão e o problema está aqui. Além disso, o comportamento da expansão está relacionado com as opções shopt
, então devemos começar a ver caso por caso ...
-
Quando você colar a string cd C:\Foo\Bar
em seu shell bash, ela será expandida e aparecerá para o interpretador como cd C:FooBar
; desta forma, ele será armazenado na variável interna $_
também.
Se você, em vez disso, colou cd "C:\Foo\Bar"
ou cd 'C:\Foo\Bar'
no $_
variável você deve encontrar C:\Foo\Bar
.
Como a expansão do Histórico é executada imediatamente após uma linha completa ser lida, antes que ela seja quebrada em palavras, você pode ficar tentado a usá-la com algum bashism mais ou menos simples, por exemplo, com alguns derivação de (talvez adicionando :p
ou :q
, ""
, análise e assim por diante ...)
!!:0 ${_//\/\/}
Este é o momento para lembrar que não é seguro começar a jogar com o caminho e nomes de arquivo , especialmente se eles vierem do prancheta do Windows (leia, em geral, a página Por que não analisam ls
? , ele está essencialmente relacionado com a possibilidade de usar tabulação, espaços e novas linhas como caracteres corretos para os nomes dos arquivos e os diretórios ...).
Além disso, quando você cola um texto capturado com o mouse , você também pode colar um espaço à esquerda. Isso pode evitar que seu comando termine no histórico (depende das opções do shell ...). Se assim for, seu seguinte !!
será um comando não controlado ... (veja um exemplo em outra resposta ). Este é um risco tangível desnecessário .
Conclusão
History expansions introduce words from the history list into the input stream, making it easy to repeat commands, insert the arguments to a previous command into the current input line, or fix errors in previous commands quickly.
Se não for fácil, começo a pensar que estamos fazendo algo errado ;-)
Ad nauseam: uma pequena experiência
Eu habilitei histverify
no shell ...
shopt -s histverify
echo C:\Foo\Bar
!!:s|C|D| {1,2}A
então eu pressiono Enter e como verificado expansão eu acho
echo D:\Foo\Bar {1,2}A
então eu pressiono Enter novamente e ele ecoa
D:FooBar 1A 2A
Isto parece indicar que o substitution failed
é gerado na expansão do histórico processado antes da expansão do Brace , então antes de tudo , e parece confirmar que o modificador s
history não (ainda) processou a substituição do caractere \
como um regex real. .