On Sat, 4 Mar 2023 09:42:02 +0100, Bernhard Voelker <mail@bernhard-voelker.de> wrote:
On 3/1/23 00:31, Robert Webb wrote:
find -H "$@" -type f -exec stat -c '%Y %n' {} + > "$TEMPF" || exit
sed -e ' s+^\('"$W"'\)[^/]*$+\1.+ t s+^\('"$W"'/\)[^/]*$+\1+ t s+^\('"$W"'.*\)/[^/]*$+\1+ ' "$TEMPF" \ |sort -k 2 -k 1,1nr \ |uniq -c -f 1 \ |sort_by \ |sed -e 's+'"$W"'+ +2'
I didn't check what the part with uniq and sort_by is doing exactly.
It is complicated because the end result I want is a list of directories, but they need to be selected and ordered based on the files they contain. So the find looks for files meeting the search terms and outputs their modification times and paths. I don't actually care about the filenames, so the first sed truncates them to just the directory path, and then there are multiple lines of the same directory paired with a modification time for each of the selected files within it. The first sort groups all the entries for the same directory together, and with the most recent modification time listed first. Then uniq chooses just that first one, so now there is one entry for each directory, paired with the mod time of the most recent file contained in it (what I was probably working on last). The second sort is to optionally sort the results either by path or mod times, and the final sed removes the time field that was just used for sorting.
Still a minor hint:
There's no need to call stat(1) again - because find(1) already has stat(3)-ed the file, and the -printf option allows to output the same information.
Yes. I'm surprised I overlooked the -printf option of find. I have used stat in find many times to get selected info displayed, and just ignored -printf. Thanks.
This is a similar case than in the find manual (sorry if split on the next line): https://www.gnu.org/software/findutils/manual/html_node/find_html/Updating-A...
stat(1): %Y time of last data modification, seconds since Epoch %n file name
find(1): %p File's name. %Tk File's last modification time in the format specified by k, which is the same as for %A.
and with k = '@': @ seconds since Jan. 1, 1970, 00:00 GMT, with fractional part.
This makes something like this - which shows the 5 newest files:
$ find -type f -printf '%T@:%p\n' | sort -k1,1n | tail -n5 | cut -d: -f 2- | xargs ls -ldog
Useful. I'll be changing the script.
Of course, that only works for file names without newline '\n' in them, but that's a different discussion.
Yep. That's a bug. Not a feature. Let's see if I ever fix that. :-) -- Robert Webb