Repository: pandas-dev/pandas

Issue:
BUG: allow as_index=False for non aggregating groupby methods
closes #4648
closes #3417



Discussion:
@jreback merge-able? pretty trivial fix, but want to get your okay on it.

looks fine

FYI I think there might be an open issue related to this (aside from the one u indicates)

might be the same or unrelelated don't know

Does this work with an index which isn't plain (i.e. not just an arange)? Don't think you're testing for that...

@hayd good call thanks

Does this resolve #3805?

@cpcloud example I had in mind was something like this (with non-boring index), from your branch:

```
In [1]: df = pd.DataFrame([[1, 2], [2, 3], [1, 4], [1, 5], [2, 6]], index=list('abcde'))

In [2]: g = df.groupby(0, as_index=False)

In [3]: g.apply(lambda x: x)
Out[3]: 
   0  1
0  1  2
1  2  3
2  1  4
3  1  5
4  2  6
```

Shouldn't this have index of original DataFrame.

@jtratner nope (just tested)

ah then i misunderstood what `as_index` was supposed to do.

So I think the thing from SO was:

```
In [34]: g = df.groupby(0)

In [35]: g.apply(lambda x: x.head(2))
Out[35]: 
     0  1
0        
1 a  1  2
  c  1  4
2 b  2  3
  e  2  6

In [36]: g = df.groupby(0, as_index=False)

In [37]: g.apply(lambda x: x.head(2))
Out[37]: 
     0  1
0        
1 a  1  2
  c  1  4
2 b  2  3
  e  2  6
```

And we expect the latter not to include the group info.

```
   0  1
a  1  2
c  1  4
b  2  3
e  2  6
```

Now I think about it, we It could be completely misusing apply here...


Resolving patch:
diff --git a/pandas/core/groupby.py b/pandas/core/groupby.py
--- a/pandas/core/groupby.py
+++ b/pandas/core/groupby.py
@@ -516,7 +516,7 @@ def _concat_objects(self, keys, values, not_indexed_same=False):
                 result = result.reindex(ax)
             else:
                 result = result.reindex_axis(ax, axis=self.axis)
-        elif self.group_keys:
+        elif self.group_keys and self.as_index:
             group_keys = keys
             group_levels = self.grouper.levels
             group_names = self.grouper.names


Test patch:
diff --git a/pandas/tests/test_groupby.py b/pandas/tests/test_groupby.py
--- a/pandas/tests/test_groupby.py
+++ b/pandas/tests/test_groupby.py
@@ -12,7 +12,8 @@
 from pandas.core.groupby import GroupByError, SpecificationError, DataError
 from pandas.core.series import Series
 from pandas.util.testing import (assert_panel_equal, assert_frame_equal,
-                                 assert_series_equal, assert_almost_equal)
+                                 assert_series_equal, assert_almost_equal,
+                                 assert_index_equal)
 from pandas.compat import(
     range, long, lrange, StringIO, lmap, lzip, map, zip, builtins, OrderedDict
 )
@@ -1178,6 +1179,34 @@ def test_groupby_as_index_corner(self):
         self.assertRaises(ValueError, self.df.groupby,
                           lambda x: x.lower(), as_index=False, axis=1)
 
+    def test_groupby_as_index_apply(self):
+        # GH #4648 and #3417
+        df = DataFrame({'item_id': ['b', 'b', 'a', 'c', 'a', 'b'],
+                        'user_id': [1,2,1,1,3,1],
+                        'time': range(6)})
+
+        g_as = df.groupby('user_id', as_index=True)
+        g_not_as = df.groupby('user_id', as_index=False)
+
+        res_as = g_as.head(2).index
+        exp_as = MultiIndex.from_tuples([(1, 0), (1, 2), (2, 1), (3, 4)])
+        assert_index_equal(res_as, exp_as)
+
+        res_not_as = g_not_as.head(2).index
+        exp_not_as = Index([0, 2, 1, 4])
+        assert_index_equal(res_not_as, exp_not_as)
+
+        res_as = g_as.apply(lambda x: x.head(2)).index
+        assert_index_equal(res_not_as, exp_not_as)
+
+        res_not_as = g_not_as.apply(lambda x: x.head(2)).index
+        assert_index_equal(res_not_as, exp_not_as)
+
+        ind = Index(list('abcde'))
+        df = DataFrame([[1, 2], [2, 3], [1, 4], [1, 5], [2, 6]], index=ind)
+        res = df.groupby(0, as_index=False).apply(lambda x: x).index
+        assert_index_equal(res, ind)
+
     def test_groupby_multiple_key(self):
         df = tm.makeTimeDataFrame()
         grouped = df.groupby([lambda x: x.year,