首页 > 解决方案 > 在 Seaborn 图中获取 LaTeX 符号,而不会弄乱 Pandas 查询

问题描述

我构造一个DataFrame这样的:

import pandas as pd
import seaborn as sns
import matplotlib.pyplot as plt

df = pd.DataFrame({
    "x": [0, 1, 0, 1],
    "y": [1, 2, 1.5, 3],
    "sigma": [1, 1, 2, 2],
})

它支持不错的query功能:

# OK!
pts = df.query("sigma < 2")
print(pts)

和情节:

sns.lineplot(data=df, x="x", y="y", hue="sigma", legend="full")
plt.show()

但我意识到我更喜欢 LaTeX 符号\sigma而不是传说中的“sigma”一词。Matplotlib 可以渲染它。我改为尝试:

SIGMA = "$\\sigma$"
df = pd.DataFrame({
    "x": [0, 1, 0, 1],
    "y": [1, 2, 1.5, 3],
    SIGMA: [1, 1, 2, 2],
})
plt.clf()
sns.lineplot(data=df, x="x", y="y", hue=SIGMA, legend="full")
plt.show()

绘图仍然有效。但现在如果我尝试查询:

# Fails!
pts = df.query(SIGMA + " < 2")
print(pts)

pandas我在查询引擎中收到一条错误消息:

Traceback (most recent call last):
  File "demo.py", line 28, in <module>
    pts = df.query(SIGMA + " < 2")
  File "/usr/local/lib/python3.6/dist-packages/pandas/core/frame.py", line 3184, in query
    res = self.eval(expr, **kwargs)
  File "/usr/local/lib/python3.6/dist-packages/pandas/core/frame.py", line 3300, in eval
    return _eval(expr, inplace=inplace, **kwargs)
  File "/usr/local/lib/python3.6/dist-packages/pandas/core/computation/eval.py", line 322, in eval
    parsed_expr = Expr(expr, engine=engine, parser=parser, env=env, truediv=truediv)
  File "/usr/local/lib/python3.6/dist-packages/pandas/core/computation/expr.py", line 827, in __init__
    self.terms = self.parse()
  File "/usr/local/lib/python3.6/dist-packages/pandas/core/computation/expr.py", line 844, in parse
    return self._visitor.visit(self.expr)
  File "/usr/local/lib/python3.6/dist-packages/pandas/core/computation/expr.py", line 437, in visit
    raise e
  File "/usr/local/lib/python3.6/dist-packages/pandas/core/computation/expr.py", line 431, in visit
    node = ast.fix_missing_locations(ast.parse(clean))
  File "/usr/lib/python3.6/ast.py", line 35, in parse
    return compile(source, filename, mode, PyCF_ONLY_AST)
  File "<unknown>", line 1
    $\sigma $<2 
    ^
SyntaxError: invalid syntax

有没有办法:

  1. 为绘图中使用的列分配不同的“显示名称”,但不用于查询,或者
  2. 适当地转义 LaTeX 字符串以便 Pandas 查询引擎可以处理它?

如果可能的话,我更喜欢 1.,因为它会使查询看起来更清晰。

标签: pythonpandasseaborn

解决方案


你可以像这样做你的情节:

sns.lineplot(data=df.rename({"sigma": SIGMA}, axis=1), x="x", y="y", hue=SIGMA, legend="full")

这会将列重命名为,SIGMA然后将其传递给绘图函数,因此绘图函数看到的是名为"$\\sigma$".

rename"sigma"默认情况下返回原始 DataFrame 的副本而不修改原始数据,因此这使您可以在其他上下文中正常使用 DataFrame 与列。然而,一个缺点是,如果数据很大,创建新的 DataFrame 可能会影响性能。在这种情况下,您可以编写一个函数来就地重命名列,绘制绘图,然后在最后恢复名称。编写一个自定义函数通常不是一个坏主意,该函数封装了您可能希望合并到绘图中的各种调整,而不会污染实际数据。


推荐阅读