简体   繁体   中英

Markers on seaborn line plot in python

New here so putting hyperlinks. My dataframe looks like this.

 HR     ICULOS  SepsisLabel PatientID
100.3      1         0          1
117.0      2         0          1
103.9      3         0          1
104.7      4         0          1
102.0      5         0          1
88.1       6         0          1

Access the whole file here . What I wanted is to add a marker on the HR graph based on SepsisLabel (See the file). Eg, at ICULOS = 249, Sepsis Label changed from 0 to 1. I wanted to show that at this point on graph, sepsis label changed. I was able to calculate the position using this code:

mark = dummy.loc[dummy['SepsisLabel'] == 1, 'ICULOS'].iloc[0]
print("The ICULOS where SepsisLabel changes from 0 to 1 is:", mark)
Output: The ICULOS where SepsisLabel changes from 0 to 1 is: 249

I Plotted the graph using the code:

plt.figure(figsize=(15,6))

ax = plt.gca()

ax.set_title("Patient ID = 1")
ax.set_xlabel('ICULOS')
ax.set_ylabel('HR Readings')
sns.lineplot(ax=ax, 
             x="ICULOS", 
             y="HR", 
             data=dummy, 
             marker = '^', 
             markersize=5, 
             markeredgewidth=1, 
             markeredgecolor='black', 
             markevery=mark)

plt.show()

This is what I got: Graph . The marker was supposed to be on position 249 only. But it is also on position 0. Why is it happening? Can someone help me out?

Thanks.

Working with markevery can be tricky in this case, as it strongly depends on there being exactly one entry for each patient and each ICULOS .

Here is an alternative approach, using an explicit scatter plot to draw the marker:

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

df = pd.DataFrame({'HR': np.random.randn(200).cumsum() + 60,
                   'ICULOS': np.tile(np.arange(1, 101), 2),
                   'SepsisLabel': np.random.binomial(2, 0.05, 200),
                   'PatientID': np.repeat([1, 2], 100)})
for patient_id in [1, 2]:
    dummy = df[df['PatientID'] == patient_id]
    fig, ax = plt.subplots(figsize=(15, 6))
    ax.set_title(f"Patient ID = {patient_id}")
    ax.set_xlabel('ICULOS')
    ax.set_ylabel('HR Readings')
    sns.lineplot(ax=ax,
                 x="ICULOS",
                 y="HR",
                 data=dummy)
    x = dummy[dummy['SepsisLabel'] == 1]["ICULOS"].values[0]
    y = dummy[dummy['SepsisLabel'] == 1]["HR"].values[0]
    ax.scatter(x=x,
               y=y,
               marker='^',
               s=5,
               linewidth=1,
               edgecolor='black')
    ax.text(x, y, str(x) + '\n', ha='center', va='center', color='red')
    plt.show()

在 sns.lineplot 上标记一个点

For your new question, here is an example how to convert the 'ICULOS' column to pandas dates. The example uses date 20210101 to correspond with ICULOS == 1 . You probably have a different starting date for each patient.

df_fb = pd.DataFrame()
df_fb['Y'] = df['HR']
df_fb['DS'] = pd.to_datetime('20210101') + pd.to_timedelta(df['ICULOS'] - 1, unit='D')

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM