Issue
I'm trying to create a 2D heatmap in Python using matplotlib, but I'm running into difficulty when it comes to handling both positive and negative values. My dataset contains values that range from very high to very low positive and negative values, which will be perfect to represent with a log scale, but the negative values would be a problem. So my idea was to represent them with different color scales.
Specifically, I would like to create two colorbars, one using a log scale for the positive values and another using a log scale for the absolute values of the negative. The positive values should be represented with a red pattern, while the negative values should be represented with a blue pattern.
Here's a simplified version of the code I have so far:
import numpy as np
import matplotlib.pyplot as plt
import matplotlib.colors
# Generate some sample data
data = np.random.randn(10, 10)
datap = np.where(data>0, data, 0)
datan = np.abs(np.where(data<0, data, 0))
# Colorbar limits
vmin = np.abs(data).min()
vmax = np.abs(data).max()
# Create the figure and axis objects
fig, ax1 = plt.subplots()
# Create the heatmap with positive values
heatmap1 = ax1.imshow(datap, cmap='Reds', norm=matplotlib.colors.LogNorm(vmin=vmin, vmax=vmax))
# Create the second axis object for the negative values
ax2 = ax1.twinx()
# Create the heatmap for the negative values
heatmap2 = ax2.imshow(datan, cmap='Blues', norm=matplotlib.colors.LogNorm(vmin=vmin, vmax=vmax))
# Add colorbars for both heatmaps
cbar1 = fig.colorbar(heatmap1, ax=ax1, pad=0.3, label='Positive Values')
cbar2 = fig.colorbar(heatmap2, ax=ax2, pad=0.1, label='Absolute Values of Negative Values')
# Show the plot
plt.show()
But the problem is that I'm not understanding how to separate the colorbars, as you can see in the result below:
I'm not sure how to properly add the second colorbar, or maybe a better way to show this dataset.
Solution
You can move the red color bar to the right side of the blue bar. Just change the position of the red bar. Note that you also have to adjust the margin of the plot so both color bars can appear in the figure. Here's an example:
import numpy as np
import matplotlib.pyplot as plt
import matplotlib.colors
# Generate some sample data
data = np.random.randn(10, 10)
datap = np.where(data>0, data, 0)
datan = np.abs(np.where(data<0, data, 0))
# Colorbar limits
vmin = np.abs(data).min()
vmax = np.abs(data).max()
# Create the figure and axis objects
fig, ax1 = plt.subplots()
# Create the heatmap with positive values
heatmap1 = ax1.imshow(datap, cmap='Reds', norm=matplotlib.colors.LogNorm(vmin=vmin, vmax=vmax))
# Create the second axis object for the negative values
ax2 = ax1.twinx()
# Create the heatmap for the negative values
heatmap2 = ax2.imshow(datan, cmap='Blues', norm=matplotlib.colors.LogNorm(vmin=vmin, vmax=vmax))
# Change red color bar position
cbaxes1 = fig.add_axes([0.85, 0.1, 0.03, 0.7])
# Add colorbars for both heatmaps
cbar1 = fig.colorbar(heatmap1, ax=ax1, pad=0.3, label='Positive Values', cax = cbaxes1)
cbar2 = fig.colorbar(heatmap2, ax=ax2, pad=0.1, label='Absolute Values of Negative Values')
# Adjust the plot margin
plt.subplots_adjust(left=0.1, bottom=0.1, right=0.8, top=0.8)
# Show the plot
plt.show()
Answered By - Guapi-zh
0 comments:
Post a Comment
Note: Only a member of this blog may post a comment.