Please read Correct Bash and shell script variable capitalization and https://mywiki.wooledge.org/Quotes to understand some of the issues in your script and copy/paste any shell script you write into https://www.shellcheck.net/ until you get the fundamentals down.
Regarding But this produces empty files - sure, for any give command cmd with
for f in *; do
cmd "$f" > "out$f"
done
you're creating an output file for each input file in the shell loop so if any input file doesn't match $4==12 in your awk script (the cmd in this case) you'll still get an output file, it'll just be empty. If you don't want that you could do:
tmp=$(mktemp)
for f in *; do
cmd "$f" > "$tmp" &&
mv -- "$tmp" "out$f"
done
and write cmd to exit with a succ/fail status like grep does when it finds a match (trivial in awk), or you could check the size of "$tmp" before the mv:
tmp=$(mktemp)
for f in *; do
cmd "$f" > "$tmp" &&
[[ -s "$tmp" ]] &&
mv -- "$tmp" "out$f"
done
You don't need a shell loop or other commands for this, though, just 1 call to awk to process all of your files at once. Using any awk in any shell on every Unix box do only this
awk -v file='random' -F'\t' '
FNR == 1 {
close(out)
f = FILENAME
sub(".*/","",f)
out = "/home/user/extra/" file "/" f
}
$4 == 12 {
print > out
}
' /home/user/data/*.txt
If you want a string instead of numeric comparison so that 12. doesn't match 12 then do $4 == "12" instead of $4 == 12.
In the above file is a poor choice of variable name to hold the name of a directory but I left it alone to avoid changing anything I didn't have to.
12.line, right? Use string comparision:$4 == "12". Also run your script through shellcheck.net and implement its suggestions.for f in /home/user/data/*.txt;.*does not expand in the assignment.