@@ -989,6 +989,8 @@ def format(
989
989
Use 'latex' to replace the characters ``&``, ``%``, ``$``, ``#``, ``_``,
990
990
``{``, ``}``, ``~``, ``^``, and ``\`` in the cell display string with
991
991
LaTeX-safe sequences.
992
+ Use 'latex-math' to replace the characters the same way as in 'latex' mode,
993
+ except for math substrings, which start and end with ``$``.
992
994
Escaping is done before ``formatter``.
993
995
994
996
.. versionadded:: 1.3.0
@@ -1105,16 +1107,28 @@ def format(
1105
1107
<td .. >NA</td>
1106
1108
...
1107
1109
1108
- Using a ``formatter`` with LaTeX ``escape``.
1110
+ Using a ``formatter`` with ``escape`` in 'latex' mode .
1109
1111
1110
- >>> df = pd.DataFrame([["123"], ["~ ^"], ["$ %#"]])
1112
+ >>> df = pd.DataFrame([["123"], ["~ ^"], ["%#"]])
1111
1113
>>> df.style.format("\\textbf{{{}}}", escape="latex").to_latex()
1112
1114
... # doctest: +SKIP
1113
1115
\begin{tabular}{ll}
1114
- {} & {0} \\
1116
+ & 0 \\
1115
1117
0 & \textbf{123} \\
1116
1118
1 & \textbf{\textasciitilde \space \textasciicircum } \\
1117
- 2 & \textbf{\$\%\#} \\
1119
+ 2 & \textbf{\%\#} \\
1120
+ \end{tabular}
1121
+
1122
+ Using ``escape`` in 'latex-math' mode.
1123
+
1124
+ >>> df = pd.DataFrame([[r"$\sum_{i=1}^{10} a_i$ a~b $\alpha \
1125
+ ... = \frac{\beta}{\zeta^2}$"], ["%#^ $ \$x^2 $"]])
1126
+ >>> df.style.format(escape="latex-math").to_latex()
1127
+ ... # doctest: +SKIP
1128
+ \begin{tabular}{ll}
1129
+ & 0 \\
1130
+ 0 & $\sum_{i=1}^{10} a_i$ a\textasciitilde b $\alpha = \frac{\beta}{\zeta^2}$ \\
1131
+ 1 & \%\#\textasciicircum \space $ \$x^2 $ \\
1118
1132
\end{tabular}
1119
1133
1120
1134
Pandas defines a `number-format` pseudo CSS attribute instead of the `.format`
@@ -1743,9 +1757,12 @@ def _str_escape(x, escape):
1743
1757
return escape_html (x )
1744
1758
elif escape == "latex" :
1745
1759
return _escape_latex (x )
1760
+ elif escape == "latex-math" :
1761
+ return _escape_latex_math (x )
1746
1762
else :
1747
1763
raise ValueError (
1748
- f"`escape` only permitted in {{'html', 'latex'}}, got { escape } "
1764
+ f"`escape` only permitted in {{'html', 'latex', 'latex-math'}}, \
1765
+ got { escape } "
1749
1766
)
1750
1767
return x
1751
1768
@@ -2344,3 +2361,36 @@ def _escape_latex(s):
2344
2361
.replace ("^" , "\\ textasciicircum " )
2345
2362
.replace ("ab2§=§8yz" , "\\ textbackslash " )
2346
2363
)
2364
+
2365
+
2366
+ def _escape_latex_math (s ):
2367
+ r"""
2368
+ All characters between two characters ``$`` are preserved.
2369
+
2370
+ The substrings in LaTeX math mode, which start with the character ``$``
2371
+ and end with ``$``, are preserved without escaping. Otherwise
2372
+ regular LaTeX escaping applies. See ``_escape_latex()``.
2373
+
2374
+ Parameters
2375
+ ----------
2376
+ s : str
2377
+ Input to be escaped
2378
+
2379
+ Return
2380
+ ------
2381
+ str :
2382
+ Escaped string
2383
+ """
2384
+ s = s .replace (r"\$" , r"ab2§=§8yz" )
2385
+ pattern = re .compile (r"\$.*?\$" )
2386
+ pos = 0
2387
+ ps = pattern .search (s , pos )
2388
+ res = []
2389
+ while ps :
2390
+ res .append (_escape_latex (s [pos : ps .span ()[0 ]]))
2391
+ res .append (ps .group ())
2392
+ pos = ps .span ()[1 ]
2393
+ ps = pattern .search (s , pos )
2394
+
2395
+ res .append (_escape_latex (s [pos : len (s )]))
2396
+ return "" .join (res ).replace (r"ab2§=§8yz" , r"\$" )
0 commit comments