66from typing import TYPE_CHECKING
77from typing import Any
88from typing import Iterable
9+ from typing import Literal
910from typing import Sequence
1011
1112from narwhals ._compliant import CompliantThen
3031 from narwhals .utils import Implementation
3132 from narwhals .utils import Version
3233
34+ VERTICAL : Literal [0 ] = 0
35+ HORIZONTAL : Literal [1 ] = 1
36+
3337
3438class PandasLikeNamespace (
3539 EagerNamespace [
@@ -223,33 +227,37 @@ def func(df: PandasLikeDataFrame) -> list[PandasLikeSeries]:
223227 context = self ,
224228 )
225229
226- def _concat_diagonal (self , dfs : Sequence [NDFrameT ], / ) -> NDFrameT :
227- """Concatenate (native) DataFrames diagonally."""
228- concat = self ._implementation .to_native_namespace ().concat
230+ @property
231+ def _concat (self ): # type: ignore[no-untyped-def] # noqa: ANN202
232+ """Return the **native** equivalent of `pd.concat`."""
233+ # NOTE: Leave un-annotated to allow `@overload` matching via inference.
234+ if TYPE_CHECKING :
235+ import pandas as pd
236+
237+ return pd .concat
238+ return self ._implementation .to_native_namespace ().concat
239+
240+ def _concat_diagonal (self , dfs : Sequence [NDFrameT ], / ) -> pd .DataFrame :
229241 if self ._implementation .is_pandas () and self ._backend_version < (3 ,):
230242 if self ._backend_version < (1 ,):
231- return concat (dfs , axis = 0 , copy = False , sort = False )
232- return concat (dfs , axis = 0 , copy = False )
233- return concat (dfs , axis = 0 )
243+ return self . _concat (dfs , axis = VERTICAL , copy = False , sort = False )
244+ return self . _concat (dfs , axis = VERTICAL , copy = False )
245+ return self . _concat (dfs , axis = VERTICAL )
234246
235- def _concat_horizontal (self , dfs : Sequence [NDFrameT ], / ) -> NDFrameT :
236- """Concatenate (native) DataFrames horizontally."""
237- concat = self ._implementation .to_native_namespace ().concat
247+ def _concat_horizontal (self , dfs : Sequence [NDFrameT ], / ) -> pd .DataFrame :
238248 if self ._implementation .is_cudf ():
239249 with warnings .catch_warnings ():
240250 warnings .filterwarnings (
241251 "ignore" ,
242252 message = "The behavior of array concatenation with empty entries is deprecated" ,
243253 category = FutureWarning ,
244254 )
245- return concat (dfs , axis = 1 )
255+ return self . _concat (dfs , axis = HORIZONTAL )
246256 elif self ._implementation .is_pandas () and self ._backend_version < (3 ,):
247- return concat (dfs , axis = 1 , copy = False )
248- return concat (dfs , axis = 1 )
257+ return self . _concat (dfs , axis = HORIZONTAL , copy = False )
258+ return self . _concat (dfs , axis = HORIZONTAL )
249259
250260 def _concat_vertical (self , dfs : Sequence [pd .DataFrame ], / ) -> pd .DataFrame :
251- """Concatenate (native) DataFrames vertically."""
252- concat = self ._implementation .to_native_namespace ().concat
253261 cols_0 = dfs [0 ].columns
254262 for i , df in enumerate (dfs [1 :], start = 1 ):
255263 cols_current = df .columns
@@ -263,8 +271,8 @@ def _concat_vertical(self, dfs: Sequence[pd.DataFrame], /) -> pd.DataFrame:
263271 )
264272 raise TypeError (msg )
265273 if self ._implementation .is_pandas () and self ._backend_version < (3 ,):
266- return concat (dfs , axis = 0 , copy = False )
267- return concat (dfs , axis = 0 )
274+ return self . _concat (dfs , axis = VERTICAL , copy = False )
275+ return self . _concat (dfs , axis = VERTICAL )
268276
269277 def concat (
270278 self , items : Iterable [PandasLikeDataFrame ], * , how : ConcatMethod
0 commit comments