This question already has answers here:
How can I change the x axis in matplotlib so there is no white space?
(2 answers)
Closed 5 years ago.
I am trying to generate a histogram from a DataFrame with seaborn enabled via the DataFrame.hist method, but I keep finding extra space added to either side of the histogram itself, as seen by the red arrows in the below picture:
How can I remove these spaces? Code to reproduce this graph is as follows:
import seaborn as sns
import pandas as pd
import numpy as np
import matplotlib.pyplot as plt
from random import seed, choice
seed(0)
df = pd.DataFrame([choice(range(250)) for _ in range(100)], columns=['Values'])
bins = np.arange(0, 260, 10)
df['Values'].hist(bins=bins)
plt.tight_layout()
plt.show()
plt.tight_layout() only has an effect for the "outer margins" of your plot (tick marks, ax labels etc.).
By default matplotlib's hist leaves an inner margin around the hist bar-plot. To disable you can do this:
ax = df['Values'].hist(bins=bins)
ax.margins(x=0)
plt.show()
Related
This question already has answers here:
Plot lower triangle in a seaborn Pairgrid
(2 answers)
Closed 5 days ago.
I would like to remove the 6 empty boxes on the top right side of the plot(pls see the figure marked in red). I tried few different arguments and it didn't work.
Here is the code I used.
import seaborn as sns
import matplotlib.pyplot as plt
import numpy as np
# Example dataset
iris = sns.load_dataset("iris")
# Create PairGrid object with subplots
g = sns.PairGrid(iris, height=1.5, aspect=1.2)
# Create scatter plots on the lower side
g.map_lower(sns.scatterplot)
# Add regression line
g.map_lower(sns.regplot)
# Add histograms
g.map_diag(sns.histplot, kde=True)
# Then include correlation values for each scatter plot.
for i, j in zip(*plt.np.triu_indices_from(g.axes, k=1)):
corr_coef = plt.np.corrcoef(iris.iloc[:, i], iris.iloc[:, j])[0][1]
g.axes[j, i].annotate(f"R = {corr_coef:.2f}", xy=(.1, .9), xycoords=g.axes[j, i].transAxes)
plt.show()
You can use corner argument like this:
g = sns.PairGrid(iris, height=1.5, aspect=1.2, corner=True)
Result:
This question already has an answer here:
Half violin plot in matplotlib
(1 answer)
Closed 2 years ago.
I would like to obtain a graph similar to the one I drew:
In the x axis the date of the collected data, and in the y axis the associated densities.
I wrote these few lines:
import matplotlib.pyplot as plt
import numpy as np
import seaborn as sns
import pandas as pd
from datetime import datetime
df = pd.DataFrame(np.random.rand(7, 100), columns=['y']*100)
df.index = pd.date_range(datetime.today(), periods=7).tolist()
sns.kdeplot(data=df, y='y', fill=True, alpha=.5, linewidth=0)
plt.show()
but of course it doesn't work. How can I modify the code to get what I imagined?
Can be done easily using statsmodels.graphics.boxplots.violinplot
from statsmodels.graphics.boxplots import violinplot
fig, ax = plt.subplots()
violinplot(data=df.values, ax=ax, labels=df.index.strftime('%Y-%m-%d'), side='right', show_boxplot=False)
fig.autofmt_xdate()
This question already has answers here:
Modify tick label text
(13 answers)
Closed 5 months ago.
I am unable to set x axis ticklabels for a seaborn lineplot correctly.
import pandas as pd
import numpy as np
import seaborn as sns
import matplotlib.pyplot as plt
df = pd.DataFrame({'a':np.random.rand(8),'b':np.random.rand(8)})
sns.set(style="darkgrid")
g = sns.lineplot(data=df)
g.set_xticklabels(['2011','2012','2013','2014','2015','2016','2017','2018'])
The years on the x axis are not aligning properly.
Whenever you set the x-ticklabels manually, you should try to first set the corresponding ticks, and then specify the labels. In your case, therefore you should do
g = sns.lineplot(data=df)
g.set_xticks(range(len(df))) # <--- set the ticks first
g.set_xticklabels(['2011','2012','2013','2014','2015','2016','2017','2018'])
As of matplotlib 3.5.0
set_xticklabels is now discouraged:
The use of this method is discouraged because of the dependency on tick positions. In most cases, you'll want to use set_xticks(positions, labels) instead.
Now set_xticks includes a new labels param to set ticks and labels simultaneously:
ax = sns.lineplot(data=df)
ax.set_xticks(range(len(df)), labels=range(2011, 2019))
# ^^^^^^
This question already has an answer here:
adjusting subplot with a colorbar
(1 answer)
Closed 3 years ago.
I am trying to use Matplotlib to plot a time series along with its spectrogram and its associated colorbar.
Below is a MCVE:
import numpy as np
import matplotlib.pyplot as plt
import scipy.signal as scignal
import random
array=np.random.random(10000)
t,f,Sxx=scignal.spectrogram(array,fs=100)
plt.subplot(211)
plt.plot(array)
plt.subplot(212)
plt.pcolormesh(Sxx)
plt.colorbar()
This code yields the following figure:
However, I would like both subplots to have the same size:
I thought of changing the orientation of the colorbar using plt.colorbar(orientation='horizontal') but I am not satisfied with the result as the subplots end up not having the same height.
Any help will be appreciated!
The reason this happens is that plt.colorbar creates a new Axes object, which "steals" space from the lower Axes (this is the reason making a horizontal colourbar also affects the two original plots).
There are a few ways to work around this; one is to create a Figure with four Axes, allocate most of the space to the left ones, and just make one invisible:
import numpy as np
import matplotlib.pyplot as plt
import scipy.signal as scignal
import random
array = np.random.random(10000)
t, f, Sxx = scignal.spectrogram(array,fs=100)
fig, axes = plt.subplots(nrows=2, ncols=2, figsize=(5, 6), gridspec_kw={'width_ratios': [19, 1]})
(ax1, blank), (ax2, ax_cb) = axes
blank.set_visible(False)
ax1.plot(array)
m = ax2.pcolormesh(Sxx)
fig.colorbar(m, cax=ax_cb)
This question already has answers here:
Matplotlib histogram with multiple legend entries
(2 answers)
Closed 4 years ago.
I want to colour different bars in a histogram based on which bin they belong to. e.g. in the below example, I want the first 3 bars to be blue, the next 2 to be red, and the rest black (the actual bars and colour is determined by other parts of the code).
I can change the colour of all the bars using the color option, but I would like to be able to give a list of colours that are used.
import numpy as np
import matplotlib.pyplot as plt
data = np.random.rand(1000)
plt.hist(data,color = 'r')
One way may be similar to approach in other answer:
import numpy as np
import matplotlib.pyplot as plt
fig, ax = plt.subplots()
data = np.random.rand(1000)
N, bins, patches = ax.hist(data, edgecolor='white', linewidth=1)
for i in range(0,3):
patches[i].set_facecolor('b')
for i in range(3,5):
patches[i].set_facecolor('r')
for i in range(5, len(patches)):
patches[i].set_facecolor('black')
plt.show()
Result: