Take the 2-minute tour ×
Unix & Linux Stack Exchange is a question and answer site for users of Linux, FreeBSD and other Un*x-like operating systems. It's 100% free, no registration required.

I'm finding that when I use find's -or operator in combination with -exec, I don't get the result I expect. When searching for .cpp and .h files, the command works as expected if I don't use -exec:

find . -name '*.cpp' -or -name '*.h'
./file1.cpp
./file1.h
./file2.cpp
./file2.h

However, when I use -exec, only the .h files seem to be passed:

find . -name '*.cpp' -or -name '*.h' -exec echo '{}' \;
./file1.h
./file2.h

It works fine when I use the more generalized approach for returning the result:

echo $(find . -name '*.cpp' -or -name '*.h')
./file1.cpp ./file1.h ./file2.cpp ./file2.h

However, I'd like to know what I'm doing wrong with -exec, as it's often more convenient. I'm using Mac OSX 10.9, but the same issue occurs in a Cygwin terminal. What's going wrong here? How can I make -exec work the way I want?

share|improve this question

1 Answer 1

up vote 5 down vote accepted

That is because your -exe action is tied to the -name "*.h" put parenthesis around the expression and it will work. the default action will -print that is why the initial expression worked.

find . \( -name '*.cpp' -or -name '*.h' \) -exec echo '{}' \;

Also for efficiency if you use | xargs instead of -exec it is a LOT faster with a large result set as it will run a single command with the list as argument instead of an individual call per returned item.

share|improve this answer
    
Thanks! I had thought that the -exec parameter could only be used once per find invocation. If this were the case, the parens would seem unnecessary. However, it makes sense because the following can also be done: find . -name '*.cpp' -exec echo '{}' \; -or -name '*.h' -exec echo '{}' \; –  wonderlr Sep 28 '14 at 18:25
    
@Rob Worth explaining why your -exe action is tied to the -name "*.h". Namely that -or has a lower order of precedence in find than -a, which is implied in between every juxtaposed set of expressions that isn't specifically separated with another operator. Also, xargs is faster than -exec echo ... \; not -exec echo ... + –  BroSlow Oct 5 '14 at 7:32

Your Answer

 
discard

By posting your answer, you agree to the privacy policy and terms of service.

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