Jak rekurencyjnie znaleźć ostatnio zmodyfikowany plik w katalogu?
Wygląda na to, że ls
nie sortuje poprawnie plików podczas wywołania rekurencyjnego:
ls -altR . | head -n 3
Jak mogę znaleźć ostatnio zmodyfikowany plik w katalogu (łącznie z podkatalogami)?
19 answers
find . -type f -printf '%T@ %p\n' | sort -n | tail -1 | cut -f2- -d" "
Dla ogromnego drzewa może być trudno zachować wszystko w pamięci.
%T@
daje Ci czas modyfikacji jak uniksowy znacznik czasu, sort -n
sortuje numerycznie, tail -1
pobiera ostatnią linię (najwyższy znacznik czasu), cut -f2 -d" "
odcina pierwsze pole (znacznik czasu) z wyjścia.
Edit: tak jak {[6] } jest prawdopodobnie tylko GNU, ajreals używa stat -c
również. Chociaż na BSD można zrobić to samo, opcje formatowania są inne (-f "%m %N"
to seem)
I przegapiłem część liczby mnogiej; jeśli chcesz więcej to najnowszy plik , po prostu podnieś argument ogonowy.
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2010-12-30 11:01:06
Po odpowiedzi@plundra, oto wersja BSD i OS X:
find . -type f -print0 | xargs -0 stat -f "%m %N" |
sort -rn | head -1 | cut -f2- -d" "
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2017-05-23 12:10:33
Zamiast sortować wyniki i przechowywać tylko te Ostatnio zmodyfikowane, możesz użyć awk, aby wydrukować tylko ten z największym czasem modyfikacji (w czasie Uniksa):
find . -type f -printf "%T@\0%p\0" | awk '
{
if ($0>max) {
max=$0;
getline mostrecent
} else
getline
}
END{print mostrecent}' RS='\0'
To powinien być szybszy sposób rozwiązania problemu, jeśli liczba plików jest wystarczająco duża.
Użyłem znaku NUL (np. '\0'), ponieważ teoretycznie nazwa pliku może zawierać dowolny znak (w tym spację i znak nowej linii).
Jeśli nie masz takich patologicznych nazw plików w systemie można również użyć znaku nowej linii:
find . -type f -printf "%T@\n%p\n" | awk '
{
if ($0>max) {
max=$0;
getline mostrecent
} else
getline
}
END{print mostrecent}' RS='\n'
Ponadto działa to również w mawk.Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2014-09-28 14:11:30
Miałem problem ze znalezieniem ostatnio zmodyfikowanego pliku pod Solarisem 10. Tam find
nie ma opcji printf
i stat
nie jest dostępna. Odkryłem następujące rozwiązanie, które działa dobrze dla mnie:
find . -type f | sed 's/.*/"&"/' | xargs ls -E | awk '{ print $6," ",$7 }' | sort | tail -1
Aby wyświetlić nazwę pliku użyj
find . -type f | sed 's/.*/"&"/' | xargs ls -E | awk '{ print $6," ",$7," ",$9 }' | sort | tail -1
Wyjaśnienie
-
find . -type f
wyszukuje i wyświetla wszystkie pliki -
sed 's/.*/"&"/'
zawija ścieżkę w cudzysłowy, aby obsłużyć białe spacje -
xargs ls -E
wysyła cytowaną ścieżkę dols
, opcji-E
upewnij się, że zwracany jest pełny znacznik czasu (format Rok-Miesiąc-Dzień godzina-minuta-sekundy-nanosekundy) -
awk '{ print $6," ",$7 }'
wypisuje tylko datę i czas -
awk '{ print $6," ",$7," ",$9 }'
wypisuje datę, czas i nazwę pliku -
sort
zwraca pliki posortowane według daty -
tail -1
zwraca tylko ostatnio zmodyfikowany plik
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2013-09-05 16:08:45
To wydaje się działać dobrze, nawet z podkatalogami:
find . -type f | xargs ls -ltr | tail -n 1
W przypadku zbyt wielu plików, doprecyzuj znalezisko.
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2013-11-29 16:19:03
Pokazuje najnowszy plik z czytelnym dla człowieka znacznikiem czasu:
find . -type f -printf '%TY-%Tm-%Td %TH:%TM: %Tz %p\n'| sort -n | tail -n1
Wynik wygląda następująco:
2015-10-06 11:30: +0200 ./foo/bar.txt
Aby wyświetlić więcej plików, zastąp -n1
wyższą liczbą
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2015-10-08 08:50:46
To daje posortowaną listę:
find . -type f -ls 2>/dev/null | sort -M -k8,10 | head -n5
Odwróć kolejność, umieszczając '- r' w Komendzie sortowania. Jeśli chcesz tylko nazwy plików, Wstaw "awk' {print $11} | / "przed' / head '
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2013-01-30 15:27:21
Na Ubuntu 13, poniżej robi to, może trochę szybciej, ponieważ odwraca sortowanie i używa "głowy" zamiast "ogona", zmniejszając pracę. Aby wyświetlić 11 najnowszych plików w drzewie:
Znajdź . - type f-printf '%T@ %P\n' | sort-n-r | head -11 | cut-f2- -d" " | sed-e 'S,^.| ,, '/xargs ls-U-L
Daje to pełną listę ls bez ponownego sortowania i pomija irytujące './ 'że' find ' umieszcza nazwę KAŻDEGO pliku.
Lub, jako bash Funkcja:
treecent () {
local numl
if [[ 0 -eq $# ]] ; then
numl=11 # Or whatever default you want.
else
numl=$1
fi
find . -type f -printf '%T@ %p\n' | sort -n -r | head -${numl} | cut -f2- -d" " | sed -e 's,^\./,,' | xargs ls -U -l
}
Mimo to większość prac została wykonana przez oryginalne rozwiązanie plundry. Dzięki plundra.Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2013-11-14 13:23:15
To rekurencyjnie zmienia czas modyfikacji wszystkich katalogów w bieżącym katalogu na najnowszy plik w każdym katalogu:
for dir in */; do find $dir -type f -printf '%T@ "%p"\n' | sort -n | tail -1 | cut -f2- -d" " | xargs -I {} touch -r {} $dir; done
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2013-05-06 00:20:50
Ten prosty cli będzie również działać:
ls -1t | head -1
Możesz zmienić -1 na liczbę plików, które chcesz wyświetlić
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2014-08-05 09:39:13
Miałem do czynienia z tym samym problemem. Muszę rekurencyjnie znaleźć najnowszy plik. znalezienie zajęło około 50 minut.
Oto mały skrypt, aby zrobić to szybciej:
#!/bin/sh
CURRENT_DIR='.'
zob () {
FILE=$(ls -Art1 ${CURRENT_DIR} | tail -n 1)
if [ ! -f ${FILE} ]; then
CURRENT_DIR="${CURRENT_DIR}/${FILE}"
zob
fi
echo $FILE
exit
}
zob
Jest to funkcja rekurencyjna, która pobiera ostatnio zmodyfikowaną pozycję katalogu. Jeśli ten element jest katalogiem, funkcja jest wywoływana rekurencyjnie i przeszukiwana do tego katalogu, itd.
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2015-10-29 14:47:33
Używam czegoś podobnego cały czas, a także top-K listy ostatnio zmodyfikowanych plików. W przypadku dużych drzew katalogów można znacznie szybciej uniknąć sortowania . W przypadku tylko top-1 Ostatnio zmodyfikowanego pliku:
find . -type f -printf '%T@ %p\n' | perl -ne '@a=split(/\s+/, $_, 2); ($t,$f)=@a if $a[0]>$t; print $f if eof()'
Na katalogu zawierającym 1,7 miliona plików, najnowszy dostaję w 3,4 s, przyspieszenie 7,5 x w porównaniu z rozwiązaniem 25,5 s za pomocą sortowania.
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2016-03-15 22:52:12
Jeśli uruchamianie stat
na każdym pliku z osobna ma spowolnić, możesz użyć xargs
, aby nieco przyspieszyć:
find . -type f -print0 | xargs -0 stat -f "%m %N" | sort -n | tail -1 | cut -f2- -d" "
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2012-10-10 12:08:08
Powyższe polecenie okazało się przydatne, ale w moim przypadku musiałem zobaczyć datę i godzinę pliku, a także miałem problem z kilkoma plikami, które mają spacje w nazwach. Oto moje rozwiązanie.
find . -type f -printf '%T@ %p\n' | sort -n | tail -1 | cut -f2- -d" " | sed 's/.*/"&"/' | xargs ls -l
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2013-12-17 15:08:53
Na Solarisie działało następujące polecenie:
find . -name "*zip" -type f | xargs ls -ltr | tail -1
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2015-11-23 12:30:42
Wolę ten, jest krótszy:
find . -type f -print0|xargs -0 ls -drt|tail -n 1
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2014-02-11 06:36:21
Napisałem pakiet pypi / github na to pytanie, ponieważ również potrzebowałem rozwiązania.
Https://github.com/bucknerns/logtail
Zainstaluj:
pip install logtail
Usage: tails changed files
logtail <log dir> [<glob match: default=*.log>]
Usage2: otwiera ostatnio zmieniony plik w edytorze
editlatest <log dir> [<glob match: default=*.log>]
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2016-08-12 19:05:48
Ignorowanie ukrytych plików-z ładnym i szybkim znacznikiem czasu
Dobrze obsługuje spacje w nazwach plików-nie powinieneś ich używać!
$ find . -type f -not -path '*/\.*' -printf '%TY.%Tm.%Td %THh%TM %Ta %p\n' |sort -nr |head -n 10
2017.01.25 18h23 Wed ./indenting/Shifting blocks visually.mht
2016.12.11 12h33 Sun ./tabs/Converting tabs to spaces.mht
2016.12.02 01h46 Fri ./advocacy/2016.Vim or Emacs - Which text editor do you prefer?.mht
2016.11.09 17h05 Wed ./Word count - Vim Tips Wiki.mht
Więcejfind
galore można znaleźć klikając na link.
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2017-01-28 06:35:19
Znajduję następujące krótsze i bardziej interpretowalne wyjście:
find . -type f -printf '%TF %TT %p\n' | sort | tail -1
Biorąc pod uwagę stałą długość znormalizowanego formatu ISO, sortowanie leksykograficzne jest w porządku i nie potrzebujemy opcji -n
na sortowaniu.
Jeśli chcesz ponownie usunąć znaczniki czasu, możesz użyć:
find . -type f -printf '%TFT%TT %p\n' | sort | tail -1 | cut -f2- -d' '
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2017-06-07 14:26:32