Does function call via @ ignore HoldFirst attribute?

andre has given a good answer. I will add a little further clarification. The function f[#]& is a different function than the function f and does not have its attributes. It is the short form of

Function[x, f[x]]

Assume

Clear[f]; SetAttributes[f, HoldFirst]

has been evaluated. Even though f is HoldFirst, both

Function[x, f[x]][1 + 1]

and

Function[x, f[x]] @ (1 + 1)

give

f[2]

When the pure function is also given the attribute HoldFirst, evaluation goes as you expect.

Function[x, f[x], HoldFirst] @ (1 + 1)

f[1 + 1]


This is intended, but is one of the main premature evaluation case when one works with unevaluated expression.

Particularly f @ expression is not equivalent to f[#]& @ expression See :

SetAttributes[f, HoldFirst]
f[1 + 1]
f[#]& @ (1 + 1)

f[1 + 1]
f[2]

but :

f @ (1 + 1)

f[1 + 1]

The @ is not responsible of the premature evaluation. The cause is rather the use of #& applied to an expression.

Edit

To confirm this, one can try :

f[#]& [1 + 1]

f[2]


There are two separate issues here, which you are confusing.

Does function call via @ ignore HoldFirst attribute?

No, it doesn't. f[x] and f@x are different textual representations of the very same expression. Writing it either way has absolutely no effect on evaluation. The parser converts both into the very same internal representation. The evaluator works with this internal representation and doesn't know how you wrote the code originally, as f[x] or f@x.

I was trying to test whether using func[x,y] is the same as func[#,y]&@x

This is an entirely different question, and has nothing to do with using the @ character. It's about using a pure function. Note that func[#,y]&@x and func[#,y]&[x] are exactly the same thing. The latter has no @ in it.

By default, any pure function behaves as if it had no attributes (such as HoldAll, etc.). Demo:

Hold[#] &[1 + 1]
(* Hold[2] *)

Let's write this using its FullForm:

Function[Hold[#]][1 + 1]

If you look up Function, you will see that we can construct a funtcion with the same behaviour using the following syntaxes too:

Function[x, Hold[x]]

or

Function[Null, Hold[#]]

If we write it this way, we get access to the third argument, where we can specify attributes. See the Function documentation page for more information.

Function[x, Hold[x], HoldAll][1 + 1]
(* Hold[1 + 1] *)