(frame: DataFrame, level, dropna: bool = True, sort: bool = True)
| 737 | |
| 738 | |
| 739 | def stack_multiple(frame: DataFrame, level, dropna: bool = True, sort: bool = True): |
| 740 | # If all passed levels match up to column names, no |
| 741 | # ambiguity about what to do |
| 742 | if all(lev in frame.columns.names for lev in level): |
| 743 | result = frame |
| 744 | for lev in level: |
| 745 | # error: Incompatible types in assignment (expression has type |
| 746 | # "Series | DataFrame", variable has type "DataFrame") |
| 747 | result = stack(result, lev, dropna=dropna, sort=sort) # type: ignore[assignment] |
| 748 | |
| 749 | # Otherwise, level numbers may change as each successive level is stacked |
| 750 | elif all(isinstance(lev, int) for lev in level): |
| 751 | # As each stack is done, the level numbers decrease, so we need |
| 752 | # to account for that when level is a sequence of ints |
| 753 | result = frame |
| 754 | # _get_level_number() checks level numbers are in range and converts |
| 755 | # negative numbers to positive |
| 756 | level = [frame.columns._get_level_number(lev) for lev in level] |
| 757 | |
| 758 | while level: |
| 759 | lev = level.pop(0) |
| 760 | # error: Incompatible types in assignment (expression has type |
| 761 | # "Series | DataFrame", variable has type "DataFrame") |
| 762 | result = stack(result, lev, dropna=dropna, sort=sort) # type: ignore[assignment] |
| 763 | # Decrement all level numbers greater than current, as these |
| 764 | # have now shifted down by one |
| 765 | level = [v if v <= lev else v - 1 for v in level] |
| 766 | |
| 767 | else: |
| 768 | raise ValueError( |
| 769 | "level should contain all level names or all level " |
| 770 | "numbers, not a mixture of the two." |
| 771 | ) |
| 772 | |
| 773 | return result |
| 774 | |
| 775 | |
| 776 | def _stack_multi_column_index(columns: MultiIndex) -> MultiIndex | Index: |
no test coverage detected