Why find and exec with multiple conditions doesn't work without parenthesis?
Well, neither work as you expect. Let's look at the one that "doesn't work" and apply the parentheses and logic that are implied.

find ~/src \( -type f -a -iname '*.cpp' \) -or \( -iname '*.h' \) -or \( -iname '*.c' \) -or \( -iname '*.hpp' \) -exec echo {} \;


No action is applied to files that end in cpp, or file system objects that end in h and c. Only file system objects that end in hpp are echoed because -exec negates the default behavior of find to print. You could add -exec echo {} \; or -print at the end of each enclosed parentheses but that's silly.

Let's fix the "one that works"

find ~/src -type f \( -iname '*.cpp' -or -iname '*.h' -or -iname '*.c' -or -iname '*.hpp' \) -exec echo {} \;