seaborn使用twinx绘图时X轴数值与对应分类变量对齐问题
问题根源
twinx()的作用是共享X轴坐标体系、仅创建独立的Y轴,你两次绘图分别使用了分类类型的BUCKET_SEGMENT_1和数值类型的PAST_DUE_DAYS作为X输入,两类变量的坐标映射逻辑完全不同,自然会出现内容挤压、无法对齐的问题。
解决方案
根据你的需求可以选择以下两种方案:
方案1:X轴坐标对齐展示(推荐)
让分桶标签和逾期天数位置一一对应,两个折线共享数值X轴,仅将顶部X轴替换为分桶标签:
import matplotlib.pyplot as plt %matplotlib inline import seaborn as sns plt.style.use("fivethirtyeight") # 计算每个分桶对应的X轴锚点位置,取每个桶的最小逾期天数作为标签位置 bucket_position = df.groupby("BUCKET_SEGMENT_1")["PAST_DUE_DAYS"].min().to_dict() x_max = df["PAST_DUE_DAYS"].max() fig, ax = plt.subplots(1,1,figsize=(10,10)) ax2 = ax.twinx() # 两次绘图都使用数值型逾期天数作为X轴,保证坐标完全对齐 sns.lineplot(x="PAST_DUE_DAYS", y= 'Percentage to Bucket Total', data=df, ax=ax, label='逾期天数维度') sns.lineplot(x="PAST_DUE_DAYS", y= 'Percentage to Bucket Total',data=df, ax=ax2, label='分桶维度') # 配置坐标轴标签与刻度 ax.set_xlim(0, x_max + 1) ax2.set_xticks(list(bucket_position.values())) ax2.set_xticklabels(list(bucket_position.keys())) ax.set_xlabel('逾期天数') ax2.set_xlabel('分桶名称') ax.set_ylabel('主Y轴:占比') ax2.set_ylabel('次Y轴:占比') plt.legend() plt.show()
方案2:完全独立双X轴
如果不需要两个X轴的位置一一对应,仅要分别展示两个维度的折线,使用twiny()创建独立X轴即可:
import matplotlib.pyplot as plt %matplotlib inline import seaborn as sns plt.style.use("fivethirtyeight") fig, ax = plt.subplots(1,1,figsize=(10,10)) # twiny()会生成共享Y轴、独立X轴的次坐标轴 ax2 = ax.twiny() sns.lineplot(x="PAST_DUE_DAYS", y= 'Percentage to Bucket Total', data=df, ax=ax, color='#1f77b4') sns.lineplot(x="BUCKET_SEGMENT_1", y= 'Percentage to Bucket Total',data=df, ax=ax2, color='#ff7f0e') ax.set_xlabel('逾期天数') ax2.set_xlabel('分桶名称') ax.set_ylabel('占桶总百分比') plt.show()
内容的提问来源于stack exchange,提问作者a.r. noureldin
相关产品推荐
相关产品推荐

