bash: how do I concatenate the output of two commands so that I can pipe them to a third?
Solution 1
You can use a subshell:
( hg status; hg status --ignored ) | awk '( $1 == "?" ) || ( $1 == "I") { print $2 }' | xargs rm -r
Solution 2
Use curly braces to group commands:
$ { echo first line; echo second line; } | grep "line"
first line
second line
(Posted as an answer from camh's comment)
Solution 3
You can use the rest of the hg status flags to show what you really want:
hg status -uriamn
That shows unknown files (u), removed files (r), ignored (i), added (a), modified (m) and does so without showing the status prefix.
Solution 4
This works for me:
echo $(a)$(b)
if you add "" you can add delimiters eg.:
echo "$(./gethostname.sh)|($(./getip.sh);"
I use this on Openwrt to broadcast my ip settings:
echo "$( uci get system.@system[0].hostname )|$( ip addr | grep inet | grep br-lan | cut -d ' ' -f 6 | cut -d '/' -f 1 );" | socat - UDP-DATAGRAM:255.255.255.255:4999,broadcast ;
Related videos on Youtube
John Lawrence Aspden
Programmer/Contractor/Consultant in Cambridge UK Lover of LISP, C and Unix. Friend of Python and ML. CV: http://www.aspden.com Clojure Blog: http://www.learningclojure.com Random Thoughts: http://johnlawrenceaspden.blogspot.com
Updated on June 07, 2020Comments
-
John Lawrence Aspden about 4 years
$ hg status
and
$ hg status --ignored
give very similar outputs. I'd like to concatenate them so I can feed them to awk, as if there were an hg status --all (or svn's svn status --no-ignore)
I'm thinking something like:
$ echo "$(hg status)" "$(hg status --ignored)" | awk ' ( $1 == "?" ) || ( $1 == "I") { print $2 }' | xargs rm -r
to make a 'make very clean indeed' command, but it seems to occasionally leave a file behind, perhaps because a newline goes missing or something.
-
Fred Foo almost 13 yearsIf you replace
rm
withecho
(or skip the last pipe), then what is the output and what should it have been? Also, there might be permission issues whererm
refuses to delete a file.
-
-
Kent almost 13 years+1 I just wrote down "why not try
hg st -iu|awk ...
?" and saw your answer shows up... -
camh almost 13 yearsThere's no need to use a subshell (another process). Instead you can use braces to group:
{ a; b; } | c
-
Ben Moss almost 13 yearsAnd I would have posted sooner, but I was trying to make an amusing anagram out of the flags ;-)
-
Mark Fox over 8 yearsI see no meaningful speed difference
time { git branch; git branch -r; } > /dev/null; time (git branch; git branch -r) > /dev/null
in fact subshell is consistently faster on my system — so @camh, what is is the advantage of a group? -
camh over 8 years@MarkFox: It's likely measurement error. The group has one less
fork()
than the subshell. It is very hard to measure a single run of things like this. You want to run it 1000 times or more to get a good feel for the performance. When I do that, the group comes out at 1.69s and the subshell at 2.36s, which is about 40% slower. -
Aaron Wallentine about 7 yearsExcellent, thank you. This is what I was looking for, trying to concatenate headers to pass to
sendmail -t
along with output of another command.