title: What is the difference between pandas agg and apply function?
body: <p>I can't figure out the difference between Pandas <code>.aggregate</code> and <code>.apply</code> functions.<br>
  Take the following as an example: I load a dataset, do a <code>groupby</code>, define a simple function,
  and either user <code>.agg</code> or <code>.apply</code>.</p>
  
  <p>As you may see, the printing statement within my function results in the same output
  after using <code>.agg</code> and <code>.apply</code>. The result, on the other hand is different. Why is that?</p>
  
  <pre><code>import pandas
  import pandas as pd
  iris = pd.read_csv('iris.csv')
  by_species = iris.groupby('Species')
  def f(x):
      ...:     print type(x)
      ...:     print x.head(3)
      ...:     return 1
  </code></pre>
  
  <p>Using <code>apply</code>:</p>
  
  <pre><code>by_species.apply(f)
  #&lt;class 'pandas.core.frame.DataFrame'&gt;
  #   Sepal.Length  Sepal.Width  Petal.Length  Petal.Width Species
  #0           5.1          3.5           1.4          0.2  setosa
  #1           4.9          3.0           1.4          0.2  setosa
  #2           4.7          3.2           1.3          0.2  setosa
  #&lt;class 'pandas.core.frame.DataFrame'&gt;
  #   Sepal.Length  Sepal.Width  Petal.Length  Petal.Width Species
  #0           5.1          3.5           1.4          0.2  setosa
  #1           4.9          3.0           1.4          0.2  setosa
  #2           4.7          3.2           1.3          0.2  setosa
  #&lt;class 'pandas.core.frame.DataFrame'&gt;
  #    Sepal.Length  Sepal.Width  Petal.Length  Petal.Width     Species
  #50           7.0          3.2           4.7          1.4  versicolor
  #51           6.4          3.2           4.5          1.5  versicolor
  #52           6.9          3.1           4.9          1.5  versicolor
  #&lt;class 'pandas.core.frame.DataFrame'&gt;
  #     Sepal.Length  Sepal.Width  Petal.Length  Petal.Width    Species
  #100           6.3          3.3           6.0          2.5  virginica
  #101           5.8          2.7           5.1          1.9  virginica
  #102           7.1          3.0           5.9          2.1  virginica
  #Out[33]: 
  #Species
  #setosa        1
  #versicolor    1
  #virginica     1
  #dtype: int64
  </code></pre>
  
  <p>Using <code>agg</code>    </p>
  
  <pre><code>by_species.agg(f)
  #&lt;class 'pandas.core.frame.DataFrame'&gt;
  #   Sepal.Length  Sepal.Width  Petal.Length  Petal.Width Species
  #0           5.1          3.5           1.4          0.2  setosa
  #1           4.9          3.0           1.4          0.2  setosa
  #2           4.7          3.2           1.3          0.2  setosa
  #&lt;class 'pandas.core.frame.DataFrame'&gt;
  #    Sepal.Length  Sepal.Width  Petal.Length  Petal.Width     Species
  #50           7.0          3.2           4.7          1.4  versicolor
  #51           6.4          3.2           4.5          1.5  versicolor
  #52           6.9          3.1           4.9          1.5  versicolor
  #&lt;class 'pandas.core.frame.DataFrame'&gt;
  #     Sepal.Length  Sepal.Width  Petal.Length  Petal.Width    Species
  #100           6.3          3.3           6.0          2.5  virginica
  #101           5.8          2.7           5.1          1.9  virginica
  #102           7.1          3.0           5.9          2.1  virginica
  #Out[34]: 
  #           Sepal.Length  Sepal.Width  Petal.Length  Petal.Width
  #Species                                                         
  #setosa                 1            1             1            1
  #versicolor             1            1             1            1
  #virginica              1            1             1            1
  </code></pre>