bash variável substituir primeira letra com a letra em [] usando manipulação de string

0

digamos que eu tenha:

variable=string

e agora gostaria de substituir os colchetes de uso pela primeira letra

${variable/firstletter/[firstletter]}

Por fim, quero usá-lo no script para modificar um padrão de expressão regular para que ele não corresponda a si mesmo:

ps -e -o time,user,pid,ppid,comm,args | grep ${variable/firstletter/[firstletter]}

Gostaria de usá-lo em vez de tubo adicional e grep -v grep ou pgrep

Além disso, talvez você saiba como obter esse comando grep com awk e não imprimir o próprio comando awk?

    
por Chris 06.02.2018 / 16:49

4 respostas

3

Você só precisa pegar o primeiro caractere do seu parâmetro, colocar entre colchetes e depois adicionar o restante:

bash-[508]$ variable=string
bash-[509]$ echo $variable
string
bash-[510]$ echo $variable to [${variable:0:1}]${variable:1}
string to [s]tring

Assim, seu comando pode ser algo como:

ps -e -i time,user,pid,ppid,comm,args | grep "[${variable:0:1}]${variable:1}"

Isso está usando a substituição de parâmetro bash em intervalos de caracteres em uma variável, dados como por onde começar e por quanto tempo a captura deve ser.

${variable:0:1} , começa no caractere 0, o início da string e pega 1 caractere. Assim, isolando a primeira letra, v .

${variable:1} , então começa no caractere 1 e, sem um intervalo definido, pega tudo até o final de $ variable, pegando ariable .

    
por 06.02.2018 / 17:14
1

Eu tenho exatamente essa função no meu .bashrc, exceto que posso ter vários padrões de pesquisa:

psg () {
    local -a patterns=()
    (( $# == 0 )) && set -- $USER
    for arg in "$@"; do
        patterns+=("-e" "[${arg:0:1}]${arg:1}");
    done
    ps -ef | grep --color=auto "${patterns[@]}"
}

e sim, eu sei que pgrep existe.

$ psg fish bash vim grep
glennj       2     1 67 09:00 ?        02:32:31 fish
glennj     153     1  0 09:00 tty2     00:00:06 fish
glennj    3122     1  0 11:08 tty3     00:00:07 fish
glennj    3964   153  0 12:14 tty2     00:00:00 vim supersecretfile
glennj    4992  3122  0 12:41 tty3     00:00:00 bash
glennj    5162  4992  0 12:45 tty3     00:00:00 grep --color=auto -e [f]ish -e [b]ash -e [v]im -e [g]rep
    
por 06.02.2018 / 18:44
0

Por favor, tente:

#!/bin/sh 

variable=rsyslogd

regex="[$(expr "$variable" : '\(.\)')]""${variable#?}"
echo "$regex"
ps -e -o time,user,pid,ppid,comm,args | grep '$regex'

Teste:

$ ./script
[r]syslogd
00:00:00 root       521     1 rsyslogd        /usr/sbin/rsyslogd -n

Isso pode falhar se o primeiro caractere da variável for especial \ [] *? etc.

    
por 06.02.2018 / 17:36
0

maybe you know how to achieve such process grep with awk and not print awk command itself?

Com o GNU awk, poderíamos excluir o próprio processo awk usando PROCINFO para obter o PID do script.

$ pattern=cron
$ ps -e -o time,user,pid,ppid,comm,args  |
  gawk -vpat="$pattern" 'NR == 1 || $3 != PROCINFO["pid"] && $0 ~ pat' 
    TIME USER       PID  PPID COMMAND         COMMAND
00:00:10 root       530     1 cron            /usr/sbin/cron -f

Altere $0 ~ pat para index($0, pat) para implementar uma correspondência de sequência fixa em vez de uma correspondência de expressões regulares.

Embora, é claro, você possa usar pgrep em combinação com ps :

$ ps -o time,user,pid,ppid,comm,args $(pgrep "$pattern")
    TIME USER       PID  PPID COMMAND         COMMAND
00:00:10 root       530     1 cron            /usr/sbin/cron -f
    
por 06.02.2018 / 17:54

Tags