My usual idiom for counting the number of occurrences of a given line in some text input is

… | sort | uniq -c | sort -n

with the last sort -n optionally used to sort lines by occurrence count. However, I recently encountered a situation where the first three lines of the data were a header, and including them with the sorting and counting greatly reduced legibility.

What's the most elegant way to merely indent the first three rows of the input (to account for the count field) but not sort them?


At the time of writing this question, my best solution is this:

… | { for i in 1 2 3; do read -r i; printf '        %s\n' "$i"; done;
      sort | uniq -c | sort -n; }

So the output gets piped to a group which reads three lines and prints them indented by 8 spaces (which appears the amount of space used by uniq -c to hold the line count and separating space), then the remainder of the input to that group is forwarded to sort and uniq.

I guess I could write the above as a shell script somewhere, perhaps with the number of lines as an argument, so I don't have to re-type that for each such use.

  • the accepted answer and the 2nd-highest voted answer (awk's built-in pipe abilities) in the first link in @Bram's comment (stackoverflow.com/questions/14562423/…) are both better than this. In fact, any text-processing job done with a shell for loop is pretty much guaranteed to be the worst possible way to do it. The awk answer is probably best suited for you - just replace the {print $0;next} with {print "<8 spaces>"$0;next} – cas Jul 31 '17 at 12:52
  • @cas: The top answer there relies on the input being a seekable file, which is not the case for me. The awk script should work and sounds like an more conicse alternative. Do you want to suggest that as an answer here as well? A shell loop only iterating over 3 lines and using only builtins to process them should be fine in terms of performance, I guess. Particularly if the awk binary isn't cached it should beat an awk call easily. And if I were to consider your comment a challenge, I could certainly come up with far worse ways to do this. ;) – MvG Aug 3 '17 at 19:30

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.