Seaborn, how to gradient color distplot depending on the x-axis value - python-3.x

I'd like to gradient-color the plot line in the Seaborn's distplot, depending on the x-axis value. For example if the value is 1, then the colour is blue, when 1.1 then it's blue and goes toward green, and so on, and so on. For example like on the plot-draft below:
The problem is, that I don't how to set colour map manually in Seaborn or how to force x-dependend coloring of the plot's curve.

Note that distplot has been deprecated. In the current seaborn version, kdeplot draws a kde curve.
You can grab the generated line with ax.get_lines(). And then create a multicolored line similar to this tutorial example.
Here is some code to demonstrate the idea (currently it would also still work with distplot):
from matplotlib import pyplot as plt
from matplotlib.collections import LineCollection
import seaborn as sns
import numpy as np
np.random.seed(1234)
data = np.random.uniform(-1, 1.1, (5, 1000)).cumsum(axis=1).ravel()
ax = sns.kdeplot(x=data)
x, y = ax.get_lines()[0].get_data()
segments = np.array([x[:-1], y[:-1], x[1:], y[1:]]).T.reshape(-1, 2, 2)
norm = plt.Normalize(x.min(), x.max())
lc = LineCollection(segments, cmap='turbo_r', norm=norm)
lc.set_array(x[:-1])
lc.set_linewidth(2)
ax.get_lines()[0].remove()
line = ax.add_collection(lc)
ax.fill_between(x, y, color='purple', alpha=0.1, hatch='xx')
ax.margins(x=0)
ax.set_ylim(ymin=0)
plt.show()

Related

problem on filing up the colour between two index values

I have a timeseries data timeseries.txt. First I select a index value (here 50) and put a red line mark on that selected index value. And I want to highlight portion before(idx-20) and after(idx+20) the red line index value on the timeseries.
I wrote this code however i am able to put the red line mark on the timeseries but while using fill_betweenx it doesnot work. I hope experts may help me overcoming this problem.Thanks.
import matplotlib.pyplot as plt
import numpy as np
input_data=np.loadtxt("timeseries.txt")
time=np.arange(len(input_data))
plt.plot(time,input_data)
idx = [50]
mark = [time[i] for i in idx]
plt.plot(idx,[input_data[i] for i in mark], marker="|",color='red',markerfacecolor='none',mew=0.4,ms=30,alpha=2.0)
plt.fill_betweenx(idx-20,idx+20 alpha=0.25,color='lightsteelblue')
plt.show()
If you are looking for just a semi-transparent rectangle, you can use patches.Rectangle to draw one. Refer here. I have updated your code to add a rectangle. See if this meets your requirement. I have used a sine wave as I didn't have your data.
import matplotlib.pyplot as plt
import numpy as np
## Create sine wave
x = np.arange(100)
input_data=np.sin(2*np.pi*3*x/100)
time=np.arange(len(input_data))
plt.plot(time,input_data)
idx = [50]
mark = [time[i] for i in idx]
plt.plot(idx,[input_data[i] for i in mark], marker="|", color='red', markerfacecolor='none', mew=0.4,ms=30,alpha=2.0)
#plt.fill_betweenx(mark,idx-20,0, alpha=0.25,color='lightsteelblue')
# Create a Rectangle patch
import matplotlib.patches as patches
from matplotlib.patches import Rectangle
plt.gca().add_patch(Rectangle((idx[0]-20, -0.15), 40, .3, facecolor = 'lightsteelblue',fill=True,alpha=0.25, lw=0))
plt.show()
EDIT
Please refer to the Rectangle documentation provided earlier in the response. You will need to adjust the start coordinates (x,y) and the height and width to see how big/small you need the Rectangle. For eg: changing the rectangle code like this...
plt.gca().add_patch(Rectangle((idx[0]-10, -0.40), 20, 0.8, facecolor = 'lightsteelblue',fill=True,alpha=0.25, lw=0))
will give you this plot.

How to change seaborn jointplot linewidth?

hexs = sns.jointplot(a,b,marker = '.', kind = "reg", height=1.476, scatter_kws={'s':2, 'linewidth':0.1},joint_kws={'line_kws':{'linewidth':'0.5'}})
I can change the scatter size and the regression line width.
but how can I change the curve width ?(the curve pointed by the black arrow)
As the name indicates, a jointplot is a combination of some other plots.
The visual aspect of the marginal subplots can be controlled via marginal_kws=.
In this case, the marginal plots are drawn using distplot. On its turn, in a distplot, the kernel density approximation is drawn with kdeplot. The parameters of this kdeplot are controlled via the kde_kws inside the marginal_kws.
from matplotlib import pyplot as plt
import seaborn as sns
tips = sns.load_dataset("tips")
g = sns.jointplot("total_bill", "tip", data=tips, marker='.', kind="reg", height=1.476,
scatter_kws={'s': 2, 'linewidth': 0.1},
joint_kws={'line_kws': {'linewidth': 0.5}},
marginal_kws={'color': 'g', 'kde_kws': {'linewidth': 0.5}})
plt.show()

Matplotlib bar plot with table formatting

I have added a table to the bottom of my plot, but there are a number of issues with it:
The right has too much padding.
The left has too little padding.
The bottom has no padding.
The cells are too small for the text within them.
The table is too close to the bottom of the plot.
The cells belonging to the row names are not colored to match those of the bars.
I'm going out of my mind fiddling with this. Can someone help me fix these issues?
Here is the code (Python 3):
import seaborn as sns
import matplotlib.pyplot as plt
import numpy as np
import matplotlib
# Set styles
plt.style.use(['seaborn-paper', 'seaborn-whitegrid'])
plt.style.use(['seaborn'])
sns.set(palette='colorblind')
matplotlib.rc("font", family="Times New Roman", size=12)
labels = ['n=1','n=2','n=3','n=4','n=5']
a = [98.8,98.8,98.8,98.8,98.8]
b = [98.6,97.8,97.0,96.2,95.4]
bar_width = 0.20
data = [a,b]
print(data)
colors = plt.cm.BuPu(np.linspace(0, 0.5, len(labels)))
columns = ('n=1', 'n=2', 'n=3', 'n=4', 'n=5')
index = np.arange(len(labels))
plt.bar(index, a, bar_width)
plt.bar(index+bar_width+.02, b, bar_width)
plt.table(cellText=data,
rowLabels=['a', 'b'],
rowColours=colors,
colLabels=columns,
loc='bottom')
plt.subplots_adjust(bottom=0.7)
plt.ylabel('Some y label which effect the bottom padding!')
plt.xticks([])
plt.title('Some title')
plt.show()
This is the output:
Update
This is working now, but in case someone else is having issues: Make sure you are not viewing your plots and the changes you make to them with IntelliJ SciView as it does not represent changes accurately and introduces some formatting issues!
I think you can fix the first problem by setting the bounding box when you make the table using bbox like this:
bbox=[0, 0.225, 1, 0.2]
where the parameters are [left, bottom, width, height].
For the second issue (the coloring), that is because the color array is not corresponding to the seaborn coloring. You can query the seaborn color palette with
sns.color_palette(palette='colorblind')
this will give you a list of the colors seaborn is using.
Check the modifications below:
import seaborn as sns
import matplotlib.pyplot as plt
import numpy as np
import matplotlib
# Set styles
plt.style.use(['seaborn-paper', 'seaborn-whitegrid'])
plt.style.use(['seaborn'])
sns.set(palette='colorblind')
matplotlib.rc("font", family="Times New Roman", size=12)
labels = ['n=1','n=2','n=3','n=4','n=5']
a = [98.8,98.8,98.8,98.8,98.8]
b = [98.6,97.8,97.0,96.2,95.4]
bar_width = 0.20
data = [a,b]
colors = sns.color_palette(palette='colorblind')
columns = ('n=1', 'n=2', 'n=3', 'n=4', 'n=5')
index = np.arange(len(labels))
fig = plt.figure(figsize=(12,9))
plt.bar(index, a, bar_width)
plt.bar(index+bar_width+.02, b, bar_width)
plt.table(cellText=data,
rowLabels=[' a ', ' b '],
rowColours=colors,
colLabels=columns,
loc='bottom',
bbox=[0, 0.225, 1, 0.2])
fig.subplots_adjust(bottom=0.1)
plt.ylabel('Some y label which effect the bottom padding!')
plt.xticks([])
plt.title('Some title')
plt.show()
I also changed the subplot adjustment to subplot_adjust(bottom=0.1) because it wasn't coming out right otherwise. Here is the output:

How to fill area under step curve using pyplot?

I have plotted two step curves using pyplot.step(), and I would like to shade in the area beneath these curves (ideally with transparent shading). pyplot.fill_between() assumes linear interpolation, whereas I want to see step interpolation, as displayed below:
How can I shade in the region beneath these curves? Transparent coloring would be great, as this would make clear where these curves overlap.
You can use the alpha value of the fill_between to make it semi-transparent.
import matplotlib.pyplot as plt
import numpy as np
x = np.linspace(0,50,35)
y = np.random.exponential(1, len(x))
y2 = np.random.exponential(1, len(x))
plt.fill_between(x,y, step="pre", alpha=0.4)
plt.fill_between(x,y2, step="pre", alpha=0.4)
plt.plot(x,y, drawstyle="steps")
plt.plot(x,y2, drawstyle="steps")
plt.show()

How to achieve the Fiji "HiLo" colormap in matplotlib image plots, to mark under and overexposed pixels

Matplotlib's colormaps do not provide the HiLo colormap for images, which is often used in microscopy. HiLo shows a gray-level gradient from low to high values, but values at the low-end are shown in blue and ones at the upper end in red.
How can one get this color-map for matplotlib images?
To achieve this one can use the 'set_under' and 'set_over' methods of the LinearSegmentedColormap class, of which the colormaps are inherited.
# minimal example
from matplotlib import cm
import matplotlib.pyplot as plt
from numpy import arange
im_array = arange(0, 256)
cmap = cm.gray
cmap.set_over(color='red')
cmap.set_under(color='blue')
fig = plt.figure()
ax = fig.add_subplot(111)
vmin = im_array.min() + 1
vmax = im_array.max() - 1
ax.imshow(im_array.reshape((16, 16)), cmap=cmap, vmin=vmin, vmax=vmax)
May be this helps someone.
Cheers!
S

Resources