Search code examples
pythonpandasmatplotlibseaborn

Make the seaborn hue legend logarithmic


I have two independent linear variables and one dependent exponential one.

x = range(100)
y = range(100)
z = [2**i for i in range(100)]
df = pd.DataFrame({"x":x,"y":y,"z":z})

sns.scatterplot(
    x=df.x,
    y=df.y,
    hue=df.z
)

x,y, linear, z hue hard to see except extreme values

  1. How can I make the hue scale logarithmic such that the pattern in the data is revealed?
  2. Can I prevent the legend from showing large numbers in scientific notation?

Pyplot only contains setters for x and y axis scales, I only found how to change the legend to discrete values.


Solution

  • For the first part of your question: You can set the hue_norm parameter of seaborn's scatterplot function.

    Changing the appearance of labels in the legend can be achieved by iterating over the text objects of the legend and altering the format.

    Both solutions combined:

    # %%
    import matplotlib.pyplot as plt
    import pandas as pd
    import seaborn as sns
    from matplotlib.colors import LogNorm
    
    x = range(100)
    y = range(100)
    z = [2**i for i in range(100)]
    df = pd.DataFrame({"x":x,"y":y,"z":z})
    
    sns.scatterplot(
        x=df.x,
        y=df.y,
        hue=df.z,
        hue_norm=LogNorm()
    )
    
    # prevent scientific notation in legend labels
    for label in plt.legend().get_texts():
        label.set_text(f"{float(label.get_text()):.0f}")
    

    enter image description here