Skip to content

implemented additionally functionality of formatters_col in to_latex #37552

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Closed
wants to merge 5 commits into from
Closed
Show file tree
Hide file tree
Changes from 3 commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
1 change: 1 addition & 0 deletions doc/source/whatsnew/v1.2.0.rst
Original file line number Diff line number Diff line change
Expand Up @@ -488,6 +488,7 @@ I/O
- Bug in output rendering of complex numbers showing too many trailing zeros (:issue:`36799`)
- Bug in :class:`HDFStore` threw a ``TypeError`` when exporting an empty :class:`DataFrame` with ``datetime64[ns, tz]`` dtypes with a fixed HDF5 store (:issue:`20594`)
- Bug in :class:`HDFStore` was dropping timezone information when exporting :class:`Series` with ``datetime64[ns, tz]`` dtypes with a fixed HDF5 store (:issue:`20594`)
- In :meth:`to_latex` ``formatters`` now handles ``fstring`` and ``callable`` paramaters (:issue:`26278`)

Plotting
^^^^^^^^
Expand Down
18 changes: 17 additions & 1 deletion pandas/core/generic.py
Original file line number Diff line number Diff line change
Expand Up @@ -3034,7 +3034,7 @@ def to_latex(
Write row names (index).
na_rep : str, default 'NaN'
Missing data representation.
formatters : list of functions or dict of {{str: function}}, optional
formatters : list of functions/str or dict of {{str: function}}, optional
Formatter functions to apply to columns' elements by position or
name. The result of each function must be a unicode string.
List must be of length equal to the number of columns.
Expand Down Expand Up @@ -3136,6 +3136,22 @@ def to_latex(
if multirow is None:
multirow = config.get_option("display.latex.multirow")

if is_list_like(formatters) and not isinstance(formatters, dict):
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

can you add an Example that uses this (e.g. similar to your test is fine)

Copy link
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I was having an issue providing an example with lambda functions in doc, so I included a simpler example.

formatter_elems_type = all(
isinstance(elem, str) or callable(elem) for elem in formatters
)
if formatter_elems_type:
formatters = [
(lambda style: lambda x: "{0:{1}}".format(x, style))(style)
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I would suggest not to use two folded lambda functions. This is not easily readable. Can it be replaced with an f-string?

Copy link
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Initially they were simpler lambda functions to take advantage of the existing callable implementation, but there was a python memory specific error where it created the first anonymous function and replicated it multiple times.

I believe this is using fstrings? At least for the substitution. But yeah I agree it's a little hard to read.

if isinstance(style, str)
else style
for style in formatters
]
else:
raise ValueError(
"Formatters elements should be f-strings or callable functions"
)

self = cast("DataFrame", self)
formatter = DataFrameFormatter(
self,
Expand Down
21 changes: 21 additions & 0 deletions pandas/tests/io/formats/test_to_latex.py
Original file line number Diff line number Diff line change
Expand Up @@ -121,6 +121,27 @@ def test_to_latex_column_format(self):
)
assert result == expected

def test_to_latex_with_float_format_list(self):
# GH: 26278
data = [[1, 2, 3], [4, 5, 6], [7, 8, 9.001]]
df = DataFrame(data, columns=["a", "b", "c"], index=["foo", "bar", "foobar"])

result = df.to_latex(formatters=["d", ".2f", lambda x: f"{x:.3f}"])
expected = _dedent(
r"""
\begin{tabular}{lrrr}
\toprule
{} & a & b & c \\
\midrule
foo & 1 & 2.00 & 3.000 \\
bar & 4 & 5.00 & 6.000 \\
foobar & 7 & 8.00 & 9.001 \\
\bottomrule
\end{tabular}
"""
)
assert result == expected

def test_to_latex_empty_tabular(self):
df = DataFrame()
result = df.to_latex()
Expand Down