Matplotlib:如何用不同线型、标记与颜色区分绘制插值数据段
Hey there! Great question—your initial idea of plotting the full interpolated curve plus the interpolated segments with distinct styles is totally feasible, and we can make it work by first tracking which values were interpolated. Let's break this down step by step.
Step 1: Track Which Values Were Interpolated
First, we need to keep a record of where the original data had missing values (since those are exactly the points that got interpolated). We'll create a boolean mask from the original DataFrame before interpolation.
import pandas as pd import matplotlib.pyplot as plt # Load your original data data = { 'datetime': ['2012-10-02 10:00:00', '2012-10-02 11:00:00', '2012-10-02 12:00:00', '2012-10-02 13:00:00', '2012-10-02 14:00:00', '2012-10-02 15:00:00', '2012-10-02 16:00:00', '2012-10-02 17:00:00', '2012-10-02 18:00:00', '2012-10-02 19:00:00', '2012-10-02 20:00:00', '2012-10-02 21:00:00', '2012-10-02 22:00:00', '2012-10-02 23:00:00'], 'Phoenix': [30.0, 30.0, 31.0, 31.0, 32.0, 17.0, 28.0, None, 9.0, None, 13.0, None, 7.0, 6.0], 'Chicago': [63.0, 63.0, 62.0, 62.0, 62.0, 51.0, None, None, 42.0, None, None, None, 48.0, 48.0] } df = pd.DataFrame(data) df['datetime'] = pd.to_datetime(df['datetime']) df.set_index('datetime', inplace=True) # Create a mask to track original missing values original_missing = df[['Phoenix', 'Chicago']].isna() # Perform interpolation df_interpolated = df.interpolate()
Step 2: Plot Full Curve + Highlight Interpolated Segments
Now we'll first plot the complete interpolated curve with a standard style, then overlay the interpolated segments with a distinct format (like dashed lines and hollow markers) to make them stand out while keeping the overall curve coherent.
# Plot the full interpolated curves with solid lines plt.plot(df_interpolated.index, df_interpolated['Phoenix'], color='#1f77b4', linestyle='-', label='Phoenix') plt.plot(df_interpolated.index, df_interpolated['Chicago'], color='#ff7f0e', linestyle='-', label='Chicago') # Highlight interpolated segments for Phoenix phoenix_interp_x = df_interpolated.index[original_missing['Phoenix']] phoenix_interp_y = df_interpolated['Phoenix'][original_missing['Phoenix']] plt.plot(phoenix_interp_x, phoenix_interp_y, color='#1f77b4', linestyle='--', marker='o', markerfacecolor='white', markersize=8, label='Phoenix (Interpolated)') # Highlight interpolated segments for Chicago chicago_interp_x = df_interpolated.index[original_missing['Chicago']] chicago_interp_y = df_interpolated['Chicago'][original_missing['Chicago']] plt.plot(chicago_interp_x, chicago_interp_y, color='#ff7f0e', linestyle='--', marker='s', markerfacecolor='white', markersize=8, label='Chicago (Interpolated)') # Add plot formatting for readability plt.legend() plt.xticks(rotation=45) plt.tight_layout() plt.ylabel('Temperature') plt.show()
Simplified Alternative: Highlight Only Interpolated Points
If you don't need to style the entire interpolated segment (just the individual points), using plt.scatter() is a simpler, cleaner approach:
# Plot full curves first plt.plot(df_interpolated.index, df_interpolated['Phoenix'], color='#1f77b4', linestyle='-', label='Phoenix') plt.plot(df_interpolated.index, df_interpolated['Chicago'], color='#ff7f0e', linestyle='-', label='Chicago') # Add scatter points for interpolated values plt.scatter(phoenix_interp_x, phoenix_interp_y, color='#1f77b4', marker='o', edgecolor='#1f77b4', facecolor='white', s=80, label='Phoenix Interpolated') plt.scatter(chicago_interp_x, chicago_interp_y, color='#ff7f0e', marker='s', edgecolor='#ff7f0e', facecolor='white', s=80, label='Chicago Interpolated') plt.legend() plt.xticks(rotation=45) plt.tight_layout() plt.ylabel('Temperature') plt.show()
Why This Works
By preserving the original missing value mask, we can precisely identify which points in the interpolated DataFrame were generated by interpolation. Plotting these points/segments with a different style creates a clear visual distinction while maintaining the overall continuity of the curve—exactly what you were aiming for.
内容的提问来源于stack exchange,提问作者Samuel

