30

I am confused by the commands @ and @@. From the documentation, I learnt that @@ is the function Apply. However, if I input Cos@@5 the output is 5, while if I input Cos@5, I get Cos[5]. By this it seems that @ rather than @@ has the function of "apply".

When I tried the function Plus, Plus@@{1,2} gave me 3 as desired, while Plus@{1,2} just gave me {1,2}. Could anyone help me with the difference (or relation) between @ and @@?

rm -rf
  • 88,781
  • 21
  • 293
  • 472
  • 2
    These are discussed in the answers to this question: http://mathematica.stackexchange.com/questions/5432/syntax-for-prefix-mode-with-multiple-arguments-using-shorthand The @@ is described at length in the documentation for Apply. @ is harder to find in the documentation: see Prefix, – Michael E2 Nov 14 '13 at 20:03
  • 3
    @Kuba, actually the documentation isn't great on these shortcuts. Nintety five percent of the time, I access the documentation on a function via ?FunctionName. But when you do type in ?@ you get nothing useful, likewise for @@. So my next step is usually a web search, but "at symbol mathematica" doesn't really return any useful results in Google either. – Jason B. Nov 14 '13 at 20:07
  • 1
    Welcome to Mathematica. Your question is very reasonable, as Jason points out. @ is the only function in Mathematica I can think of that apparently has no name in English. – DavidC Nov 14 '13 at 20:13
  • 1
    @Kuba, when I type ?@@ inside a notebook, that is not what I get as the output. To find that, I have to specifically open up the documentation center from the Help menu and type it into the search box. – Jason B. Nov 14 '13 at 20:22
  • @Hector I like the discussion but it is offtopic so I vote for deleting those comments to not confuse others. I admit that documentation is not perfect :). – Kuba Nov 14 '13 at 20:31
  • @DavidCarraher Actually I find Prefix is confusing. The input f@x is processed to be equivalent to f[x], and is not the same as Prefix. The @ sign as input is interpreted by syntax rules; I don't think it is translated as a real function. I realize on rereading what I wrote above is rather misleading! This is a better reference: http://reference.wolfram.com/mathematica/tutorial/SpecialWaysToInputExpressions.html – Michael E2 Nov 14 '13 at 21:56
  • @JasonB If you select @@ and execute the menu command Help > Find Selected Function (cmd-shift-F on a Mac or F1 on Windows) you get a link to the page for Apply respectively. For @, you get a link to Prefix, which is not what is wanted. This has been mentioned before on this site, but I can't find where. – Michael E2 Nov 14 '13 at 22:00
  • Related: http://mathematica.stackexchange.com/questions/30425/when-is-fg-not-the-same-as-fg – Michael E2 Nov 14 '13 at 22:06
  • @MichaelE2 Your clarification is helpful. So Prefix is not the same as @ and the latter remains nameless. – DavidC Nov 14 '13 at 22:09

3 Answers3

23

I can see the source of your confusion: If you use Head[f[x]] and Head[5] you get f and Integer respectively. Then, you read the documentation

Apply[f,expr] or f@@expr replaces the head of expr by f.

and you expect Cos@@5 to replace the Integer head by Cos. The way I explain it to myself is by saying Mathematica has two (types of) heads ;-) One type is for expressions such as f[x] and the other is for expressions such as 5. I even have names for them: explicit and implicit heads. Then I conclude: Apply replaces explicit heads only.

Now, in {1,2}, the head is an explicit one. Thus, Plus@@{1,2}=Plus@@List[1,2]=Plus[1,2]=3.

The @ symbol is easier to understand. f@x is just f[x]. So, Plus@{1,2}=Plus[List[1,2]] and the result is List[1,2] because you are not adding anything to List[1,2]. If you want to add something to List[1,2], it must be included as another parameter to Plus. Try Plus[List[1,2],a].


As mentioned in the comments, the documentation does not warn about these two types of heads. If you look closely, you will find a warning in Possible Issues in Apply and in the 3rd statement within details in AtomQ. I would have expected some clarification in Everything Is an Expression. A naive reading of it suggests that 5 and Integer[5] are the same thing.

Hector
  • 6,428
  • 15
  • 34
  • 3
    The chief difference between the two is the whether AtomQ returns True or not. If it does, then Apply doesn't work on it. – rcollyer Nov 14 '13 at 20:28
  • Even understanding that distinction, is there some sense to f@@5 simply discarding the f ? Some example where that is actually used? – george2079 Nov 14 '13 at 21:25
  • @Hector Thanks for your comment. It makes sense to me. Could you say more about the meaning of 'Head'. The help document gives some examples, but doesn't give a description or a definition. –  Nov 14 '13 at 21:35
  • 3
    @george2079: In f@@5, the problem is not about "discarding" the f but rather that there is no (explicit) head to be replaced. Again, f@@Integer[5] = f[5] because Integer[5] has an explicit head Integer. On the other hand, 5 also has head Integer but it is implicit. Implicit heads are useful for pattern matching, but they are not really there ... – Hector Nov 14 '13 at 21:35
  • @hongchaniyi: After you read this link: Everything is an Expression, play with TreeForm. – Hector Nov 14 '13 at 21:41
  • @george2079 an "exception" to what Hector said about explicit heads is Complex. AtomQ[Complex[1, 2]] returns True, but it is interpreted as a single indivisible (except mathematically) unit. – rcollyer Nov 15 '13 at 04:22
  • @george2079: An "exception" to what rcollyer wrote about AtomQ is the following: myAtom /: AtomQ[myAtom[__]] := True; f@@myAtom[1, 2, 3] returns f[1, 2, 3] even though AtomQ[myAtom[1, 2, 3]] returns True. I'll write a full question about this. – Hector Nov 15 '13 at 04:42
  • @rcollyer: Apparently, the criteria is not AtomQ but Length[exp]==0. See Anon's comment in this follow-up question. – Hector Nov 15 '13 at 07:24
  • Interesting. I'll have to play with it at some point. – rcollyer Nov 15 '13 at 13:10
10

I like to think about @@ as a Frankstein decapitation operator. It take out the Head of the old expression and replace by the new one. And @@@ as a mass Frankstein decapitation operator. It get inside each list element and apply @@ to each element inside the list.

To understand what Head means, use FullForm. For example, in the list l={1,2,3} if you apply FullForm@lyou get List[1,2,3], where List is the Head of the expression. If you want to sum the list, you can use Plus@@l, so you change List[1,2,3] by Plus[1,2,3]. List was decapted and replaced by Plus.

If you have l={{1,2},{2,3}} (that is equivalent to List[List[1,2],List[2,3]]), if you use Plus@@@l, you get {3,5}. Plus get into the list, and execute @@ in each element.

Murta
  • 26,275
  • 6
  • 76
  • 166
2

You may think of it as follows: @ applies a single-parameter function to a single argument, and @@ applies a multi-parameter function to a list of arguments (effectively, replacing its head List with the function). And, as a bonus, @@ works not only on lists with the List head, it can replace any head of a structured expression (but not heads of atomic expressions like numbers).

Vladimir Reshetnikov
  • 7,213
  • 27
  • 75
  • 2
    This description hides the fundamental feature of Apply that it replaces one head with another. Technically, a multi-parameter function is applied to a Sequence of arguments, not a List (or any other head there was around them, which gets "eaten up" by Apply). – Leonid Shifrin Nov 14 '13 at 20:51
  • @Vladimir Thanks for your reply. However, if I input Permutations@{x,y}, I have {{x,y},{y,x}}. It seems @ also apply to a set of argument. –  Nov 14 '13 at 21:06
  • @hongchaniyi It's just that some functions accept a signle argument that is itself a list. – Vladimir Reshetnikov Nov 14 '13 at 21:07
  • 2
    @hongchaniyi: It might help if you visualize the {} as having an explicit head: Permutations@{x,y} = Permutations@List[x,y] = Permutations[List[x,y]] – Hector Nov 14 '13 at 21:19