Ottieni la directory più recente (non il file più recente)


15

La mia cartella parentha il seguente contenuto:

A.Folder B.Folder C.File

Ha sia cartelle che file all'interno. B.Folderè più recente. Ora voglio solo ottenere B.Folder, come ho potuto raggiungere questo obiettivo? Ho provato questo

ls -ltr ./parent | grep '^d' | tail -1

ma mi dà drwxrwxr-x 2 user user 4096 Jun 13 10:53 B.Folder, ma ho solo bisogno del nome B.Folder.


1
usare questols -ltr ./parent | grep '^d' | tail -1| awk '{print $NF}'
بارپابابا

L'uso di awk funziona, ma voglio vedere se esiste una soluzione più pulita. :)
Daniel,

trova . -maxdepth 1 -type d | TZ = utc xargs ls -ld --full-time | sort -k 6
ctrl-alt-delor

Risposte:


24

Prova questo:

$ ls -td -- */ | head -n 1

-tle opzioni effettuano l' lsordinamento in base al tempo di modifica, prima il più recente.

Se vuoi rimuovere /:

$ ls -td -- */ | head -n 1 | cut -d'/' -f1

1
Come sbarazzarsi di barra /?
Daniel,

Questo non funziona se ci si trova in un'altra cartella. Voglio dire ls -td -- ./parent | head -n 1, non mi dà i risultati corretti, DEVO usare subshell come cd ./parentogni volta ed eseguire questo comando? Qualche soluzione?
Daniel,

@Daniel: è necessario eseguire la mia risposta nella directory di lavoro corrente per farlo funzionare. Altrimenti, è necessario utilizzare un percorso relativo come la risposta di Herson.
cuonglm,

La rimozione dell'ultimo / non funziona. Esempio: / home / cuo / bin / Previsto: / home / cuo / bin
Marius

5
ls -td -- ./parent/*/ | head -n1 | cut -d'/' -f2

La differenza rispetto alla soluzione di Herson è la barra dopo *, che fa sì che la shell ignori tutti i file non dir. Differenza rispetto a Gnouc , funzionerà se ti trovi in ​​un'altra cartella.

Cut ha bisogno di conoscere il numero di directory principali (2) per eliminare il '/' finale. Se non lo hai, usa

VAR=$(ls -dt -- parent/*/ | head -n1); echo "${VAR::-1}"

3

Risposta obbligatoria zsh:

latest_directory=(parent/*(/om[1]))

I caratteri tra parentesi sono qualificazioni glob : /per abbinare solo le directory, omper ordinare le partite in base all'età crescente e [1]per conservare solo la prima (cioè la più recente) partita. Aggiungi Nse vuoi ottenere un array vuoto (normalmente ottieni un array a 1 elemento) se non c'è una sottodirectory di parent.

In alternativa, supponendo che parentnon contenga alcun carattere di gorgogliamento della shell:

latest_directory='parent/*(/om[1])'; latest_directory=$~latest_directory

Se non hai zsh ma hai recenti strumenti GNU (cioè Linux non incorporato o Cygwin), puoi usarlo find, ma è ingombrante. Ecco un modo:

latest_directory_inode=$(find parent -mindepth 1 -maxdepth 1 -type d -printf '%Ts %i\n' | sort -n | sed -n '1 s/.* //p')
latest_directory=$(find parent -maxdepth 1 -inum "$latest_directory_inode")

C'è una soluzione semplice con ls, che funziona fino a quando nessun nome di directory contiene righe o caratteri non stampabili (su alcuni sistemi):

latest_directory=$(ls -td parent/*/ | head -n1)
latest_directory=${latest_directory%/}


2

Il comando seguente eseguirà il lavoro anche nel caso in cui il nome della directory contenga spazio:

cp `find . -mindepth 1 -maxdepth 1 -type d  -exec stat --printf="%Y\t%n\n" {} \;  |sort -n -r |head -1 |cut -f2'`/* /target-directory/.

La spiegazione aggiornata delle cose nei backtick è:

  • . - la directory corrente (potresti voler specificare un percorso assoluto qui)
  • -mindepth/-maxdepth - limita il comando find solo ai figli immediati della directory corrente
  • -type d - solo directory
  • -exec stat .. - genera il tempo modificato e il nome della directory da find separati da una scheda (e non da uno spazio)
  • sort -n -r |head -1 | cut -f2 - date ordina la directory e restituisce l'intero nome dell'ultima modifica (anche se contiene dello spazio come scheda delimitatore predefinita tagliata)
Utilizzando il nostro sito, riconosci di aver letto e compreso le nostre Informativa sui cookie e Informativa sulla privacy.
Licensed under cc by-sa 3.0 with attribution required.