@@ -248,7 +248,11 @@ def aggregate(self, func=None, *args, engine=None, engine_kwargs=None, **kwargs)
248
248
data .to_frame (), func , * args , engine_kwargs = engine_kwargs , ** kwargs
249
249
)
250
250
index = self .grouper .result_index
251
- return self .obj ._constructor (result .ravel (), index = index , name = data .name )
251
+ result = self .obj ._constructor (result .ravel (), index = index , name = data .name )
252
+ if not self .as_index :
253
+ result = self ._insert_inaxis_grouper (result )
254
+ result .index = default_index (len (result ))
255
+ return result
252
256
253
257
relabeling = func is None
254
258
columns = None
@@ -268,6 +272,9 @@ def aggregate(self, func=None, *args, engine=None, engine_kwargs=None, **kwargs)
268
272
# columns is not narrowed by mypy from relabeling flag
269
273
assert columns is not None # for mypy
270
274
ret .columns = columns
275
+ if not self .as_index :
276
+ ret = self ._insert_inaxis_grouper (ret )
277
+ ret .index = default_index (len (ret ))
271
278
return ret
272
279
273
280
else :
@@ -287,23 +294,24 @@ def aggregate(self, func=None, *args, engine=None, engine_kwargs=None, **kwargs)
287
294
288
295
# result is a dict whose keys are the elements of result_index
289
296
index = self .grouper .result_index
290
- return Series (result , index = index )
297
+ result = Series (result , index = index )
298
+ if not self .as_index :
299
+ result = self ._insert_inaxis_grouper (result )
300
+ result .index = default_index (len (result ))
301
+ return result
291
302
292
303
agg = aggregate
293
304
294
305
def _aggregate_multiple_funcs (self , arg ) -> DataFrame :
295
306
if isinstance (arg , dict ):
296
-
297
- # show the deprecation, but only if we
298
- # have not shown a higher level one
299
- # GH 15931
300
- raise SpecificationError ( "nested renamer is not supported" )
301
-
302
- if any (isinstance (x , (tuple , list )) for x in arg ):
307
+ if self . as_index :
308
+ # GH 15931
309
+ raise SpecificationError ( "nested renamer is not supported" )
310
+ else :
311
+ # GH#50684 - This accidentally worked in 1.x
312
+ arg = list ( arg . items ())
313
+ elif any (isinstance (x , (tuple , list )) for x in arg ):
303
314
arg = [(x , x ) if not isinstance (x , (tuple , list )) else x for x in arg ]
304
-
305
- # indicated column order
306
- columns = next (zip (* arg ))
307
315
else :
308
316
# list of functions / function names
309
317
columns = []
@@ -313,10 +321,13 @@ def _aggregate_multiple_funcs(self, arg) -> DataFrame:
313
321
arg = zip (columns , arg )
314
322
315
323
results : dict [base .OutputKey , DataFrame | Series ] = {}
316
- for idx , (name , func ) in enumerate (arg ):
324
+ with com .temp_setattr (self , "as_index" , True ):
325
+ # Combine results using the index, need to adjust index after
326
+ # if as_index=False (GH#50724)
327
+ for idx , (name , func ) in enumerate (arg ):
317
328
318
- key = base .OutputKey (label = name , position = idx )
319
- results [key ] = self .aggregate (func )
329
+ key = base .OutputKey (label = name , position = idx )
330
+ results [key ] = self .aggregate (func )
320
331
321
332
if any (isinstance (x , DataFrame ) for x in results .values ()):
322
333
from pandas import concat
@@ -396,12 +407,18 @@ def _wrap_applied_output(
396
407
)
397
408
if isinstance (result , Series ):
398
409
result .name = self .obj .name
410
+ if not self .as_index and not_indexed_same :
411
+ result = self ._insert_inaxis_grouper (result )
412
+ result .index = default_index (len (result ))
399
413
return result
400
414
else :
401
415
# GH #6265 #24880
402
416
result = self .obj ._constructor (
403
417
data = values , index = self .grouper .result_index , name = self .obj .name
404
418
)
419
+ if not self .as_index :
420
+ result = self ._insert_inaxis_grouper (result )
421
+ result .index = default_index (len (result ))
405
422
return self ._reindex_output (result )
406
423
407
424
def _aggregate_named (self , func , * args , ** kwargs ):
@@ -577,7 +594,7 @@ def true_and_notna(x) -> bool:
577
594
filtered = self ._apply_filter (indices , dropna )
578
595
return filtered
579
596
580
- def nunique (self , dropna : bool = True ) -> Series :
597
+ def nunique (self , dropna : bool = True ) -> Series | DataFrame :
581
598
"""
582
599
Return number of unique elements in the group.
583
600
@@ -629,7 +646,12 @@ def nunique(self, dropna: bool = True) -> Series:
629
646
# GH#21334s
630
647
res [ids [idx ]] = out
631
648
632
- result = self .obj ._constructor (res , index = ri , name = self .obj .name )
649
+ result : Series | DataFrame = self .obj ._constructor (
650
+ res , index = ri , name = self .obj .name
651
+ )
652
+ if not self .as_index :
653
+ result = self ._insert_inaxis_grouper (result )
654
+ result .index = default_index (len (result ))
633
655
return self ._reindex_output (result , fill_value = 0 )
634
656
635
657
@doc (Series .describe )
@@ -643,12 +665,11 @@ def value_counts(
643
665
ascending : bool = False ,
644
666
bins = None ,
645
667
dropna : bool = True ,
646
- ) -> Series :
668
+ ) -> Series | DataFrame :
647
669
if bins is None :
648
670
result = self ._value_counts (
649
671
normalize = normalize , sort = sort , ascending = ascending , dropna = dropna
650
672
)
651
- assert isinstance (result , Series )
652
673
return result
653
674
654
675
from pandas .core .reshape .merge import get_join_indexers
@@ -786,7 +807,11 @@ def build_codes(lev_codes: np.ndarray) -> np.ndarray:
786
807
787
808
if is_integer_dtype (out .dtype ):
788
809
out = ensure_int64 (out )
789
- return self .obj ._constructor (out , index = mi , name = self .obj .name )
810
+ result = self .obj ._constructor (out , index = mi , name = self .obj .name )
811
+ if not self .as_index :
812
+ result .name = "proportion" if normalize else "count"
813
+ result = result .reset_index ()
814
+ return result
790
815
791
816
def fillna (
792
817
self ,
@@ -1274,7 +1299,7 @@ def aggregate(self, func=None, *args, engine=None, engine_kwargs=None, **kwargs)
1274
1299
result .columns = result .columns .droplevel (- 1 )
1275
1300
1276
1301
if not self .as_index :
1277
- self ._insert_inaxis_grouper_inplace (result )
1302
+ result = self ._insert_inaxis_grouper (result )
1278
1303
result .index = default_index (len (result ))
1279
1304
1280
1305
return result
@@ -1386,7 +1411,7 @@ def _wrap_applied_output(
1386
1411
return self .obj ._constructor_sliced (values , index = key_index )
1387
1412
else :
1388
1413
result = self .obj ._constructor (values , columns = [self ._selection ])
1389
- self ._insert_inaxis_grouper_inplace (result )
1414
+ result = self ._insert_inaxis_grouper (result )
1390
1415
return result
1391
1416
else :
1392
1417
# values are Series
@@ -1443,7 +1468,7 @@ def _wrap_applied_output_series(
1443
1468
result = self .obj ._constructor (stacked_values , index = index , columns = columns )
1444
1469
1445
1470
if not self .as_index :
1446
- self ._insert_inaxis_grouper_inplace (result )
1471
+ result = self ._insert_inaxis_grouper (result )
1447
1472
1448
1473
return self ._reindex_output (result )
1449
1474
@@ -1774,7 +1799,9 @@ def _gotitem(self, key, ndim: int, subset=None):
1774
1799
subset ,
1775
1800
level = self .level ,
1776
1801
grouper = self .grouper ,
1802
+ exclusions = self .exclusions ,
1777
1803
selection = key ,
1804
+ as_index = self .as_index ,
1778
1805
sort = self .sort ,
1779
1806
group_keys = self .group_keys ,
1780
1807
observed = self .observed ,
@@ -1790,19 +1817,6 @@ def _get_data_to_aggregate(self) -> Manager2D:
1790
1817
else :
1791
1818
return obj ._mgr
1792
1819
1793
- def _insert_inaxis_grouper_inplace (self , result : DataFrame ) -> None :
1794
- # zip in reverse so we can always insert at loc 0
1795
- columns = result .columns
1796
- for name , lev , in_axis in zip (
1797
- reversed (self .grouper .names ),
1798
- reversed (self .grouper .get_group_levels ()),
1799
- reversed ([grp .in_axis for grp in self .grouper .groupings ]),
1800
- ):
1801
- # GH #28549
1802
- # When using .apply(-), name will be in columns already
1803
- if in_axis and name not in columns :
1804
- result .insert (0 , name , lev )
1805
-
1806
1820
def _indexed_output_to_ndframe (
1807
1821
self , output : Mapping [base .OutputKey , ArrayLike ]
1808
1822
) -> DataFrame :
@@ -1825,7 +1839,7 @@ def _wrap_agged_manager(self, mgr: Manager2D) -> DataFrame:
1825
1839
mgr .set_axis (1 , index )
1826
1840
result = self .obj ._constructor (mgr )
1827
1841
1828
- self ._insert_inaxis_grouper_inplace (result )
1842
+ result = self ._insert_inaxis_grouper (result )
1829
1843
result = result ._consolidate ()
1830
1844
else :
1831
1845
index = self .grouper .result_index
@@ -1918,7 +1932,7 @@ def nunique(self, dropna: bool = True) -> DataFrame:
1918
1932
1919
1933
if not self .as_index :
1920
1934
results .index = default_index (len (results ))
1921
- self ._insert_inaxis_grouper_inplace (results )
1935
+ results = self ._insert_inaxis_grouper (results )
1922
1936
1923
1937
return results
1924
1938
0 commit comments