Remove todas as versões menos recentes - sem timestamp

3

Eu tenho uma grande coleção de arquivos que se parece com isso:

Some Name da-1234567-1.py
Some Name da-1234567-2.py
Some Name da-1234567-4.py
Other Name di-5678912-3.py
Other Name di-5678912-4.py
Other Name di-5678912-5.py

Gostaria de remover todas as versões e manter apenas:

Some Name da-1234567-4.py
Other Name di-5678912-5.py

Sei que minha pergunta é semelhante a Localize a última versão de pasta / arquivo e remova - nenhum dado de registro de data e hora . No entanto, sua resposta não funciona para mim e meu conhecimento de bash e / ou expressão regular é insuficiente para alterar a solução para atender minhas necessidades. Infelizmente eu não tenho a pontuação de reputação para comentar, portanto, não vejo outra opção do que postar uma nova pergunta.

Eu tentei o seguinte da pergunta acima:

for file in *.*
do
  [[ -d "$file" || $file =~ _[[:digit:]]{3}\. ]] && continue
  echo -n "Considering $file: " >&2

  extn="${file/*.}"
  versions=("$file")
  keep="$file"

  # Look at matching files
  for version in "${file%.$extn}"_???."$extn"
  do
      [[ -f "$version" ]] || continue

      # Save every one. Identify the current last
      versions+=("$version")
      keep="$version"
      echo -n "$version " >&2
  done
  echo "==> keep $keep" >&2

  # Delete them all except the last
  for version in "${versions[@]}"
  do
      [[ "$version" != "$keep" ]] && echo rm -f -- "$version"
  done
  [[ "$keep" != "$file" ]] && echo mv -f -- "$keep" "$file"
done

Eu percebo que provavelmente dá errado nesta parte:       $file =~ _[[:digit:]]{3}\. , já que ao contrário da questão acima, o final do meu arquivo é -n e não _nnn, mas não vejo como consertá-lo.

    
por YStimmer 04.06.2018 / 22:15

2 respostas

1

Ferramentas one-liner de ferramentas de software, usando ls -v e sort -V que classificam por número de versão:

{ ls -Qrv *.py |rev | uniq -f 1 | rev; ls -Q *.py; } | sort -V | uniq -u | xargs rm

Usar uniq -f 1 depende do formato de nomenclatura do arquivo ser consistente - os rev s adjacentes são necessários porque -f não tem outra maneira de ignorar o último campo.

    
por 05.06.2018 / 06:57
1

com zsh :

# all *.<number>.py files in "n"umerical order
files=(*-<->.py(n))

# associative array whose key is the part before the last "-"
typeset -A latest
for f ($files) latest[${f%-*}]=$f

# plain array with the values of the associative array
keep=($latest)

# array disjunction:
echo rm -- ${files:|keep}

(remova echo se estiver feliz).

Isso não faz nenhuma suposição sobre quais caracteres o resto dos nomes de arquivo pode conter. Com bash (ou zsh ou ksh ) e ferramentas GNU:

xargs -r0a <(printf '%s
# all *.<number>.py files in "n"umerical order
files=(*-<->.py(n))

# associative array whose key is the part before the last "-"
typeset -A latest
for f ($files) latest[${f%-*}]=$f

# plain array with the values of the associative array
keep=($latest)

# array disjunction:
echo rm -- ${files:|keep}
' *-*.py | grep -zEe '-[[:digit:]]+\.py$' | sort -zrV | awk -vRS='
xargs -r0a <(printf '%s%pre%' *-*.py |
  grep -zEe '-[[:digit:]]+\.py$' |
  sort -zrV |
  awk -vRS='%pre%' -vORS='%pre%' '
    {key = $0; sub(/-[^-]*$/, "", key)}
    seen[key]++') echo rm --
' -vORS='%pre%' ' {key = $0; sub(/-[^-]*$/, "", key)} seen[key]++') echo rm --
    
por 05.06.2018 / 11:11

Tags