vertical line in histogram with pyplot - python-2.7

i've computed an Otsu's thresholding for a kinect depth image and now i want point out the optimal thresholding value on the histogram, using for example axvline with pyplot in opencv2.
I'm a beginner with python and programming too, this is the specific part of my code:
fig, (ax1, ax2, ax3) = plt.subplots(1, 3, figsize=(8, 2.5))
ax1.imshow(img)
ax1.set_title('Original')
ax1.axis('off')
ax2.hist(img)
ax2.set_title('Histogram')
plt.axvline(x=thresh, color='r', linestyle='dashed', linewidth=2)
ax3.imshow(binary, cmap=plt.cm.gray)
ax3.set_title('Thresholded')
ax3.axis('off')
plt.show()
but i don't know why, i obtain the vertical line on the thresholded plot
what am i doing wrong??
thanks

works for me:
from scipy.misc import imread, imresize
import matplotlib.pyplot as plt
f = r"C:\Users\Public\Pictures\Sample Pictures\Lighthouse.jpg"
img = imread(f)[:, :, 0]
fig, (ax1, ax2, ax3) = plt.subplots(1, 3, figsize=(8, 2.5))
ax1.imshow(img)
ax1.set_title('Original')
ax1.axis('off')
thresh = 100
ax2.hist(img)
ax2.set_title('Histogram')
ax2.axvline(x=thresh, color='r', linestyle='dashed', linewidth=2)
ax3.imshow(img, cmap=plt.cm.gray)
ax3.set_title('Thresholded')
ax3.axis('off')
plt.show()

Related

Animating Steronets

I have been looking around and have got to nowhere with this. I am trying to animate the poles on a stereonet diagram. However, the poles do not appear at the location that they should be in.
Figure 1 is the animated pole plot while Figure 2 is how the plot should be. I was wondering if anyone had an idea on how to proceed with this?
import matplotlib as mpl
mpl.use("TkAgg")
from matplotlib import pyplot as plt
from matplotlib import animation
import numpy as np
import mplstereonet
fig, ax = mplstereonet.subplots()
fig2, ax1 = mplstereonet.subplots()
ax.grid(True)
ax1.grid(True)
# Assume a strike and dip with a random variance.
# Current values should plot the poles at either 0, 180
strike, dip = 90, 80
num = 10
strikes = strike + 10 * np.random.randn(num)
dips = dip + 10 * np.random.randn(num)
poles, = ax.pole([], [], 'o')
def init():
poles.set_data([], [])
return poles,
def animate(i):
poles.set_data(strikes[:i], dips[:i])
return poles,
anim = animation.FuncAnimation(fig, animate, init_func=init,
frames = len(strikes), interval = 100, blit=True, repeat=False)
poles1 = ax1.pole(strikes, dips, 'o') # This is how the final image should look like
plt.show()

imshow a gray image and a binary image python

I have a grayscale image and a binary image, and I want to plot them side by side using hstack. It looks like there is kind of adjustment that been made yielding to darken the binary. Anybody faced this problem?
Here is my code
O = (self.img >= t) * 1
I = img
both = np.hstack((I, O))
imshow(both, cmap='gray')
show()
This is to demonstrate a somewhat different from your case which I don't know of its data. I suspect that all the values in your array 'O' are zero, thus, the plot came out as a black pane.
import numpy as np
import matplotlib.pyplot as plt
fig=plt.figure(figsize=(8, 4))
# make up some data for demo purposes
raw = np.random.randint(10, size=(6,6))
# apply some logic operatioin to the data
O = (raw >= 5) * 1 # get either 0 or 1 in the array
I = np.random.randint(10, size=(6,6)) # get 0-9 in the array
# plot each image ...
# ... side by side
fig.add_subplot(1, 2, 1) # subplot one
plt.imshow(I, cmap=plt.cm.gray)
fig.add_subplot(1, 2, 2) # subplot two
# my data is OK to use gray colormap (0:black, 1:white)
plt.imshow(O, cmap=plt.cm.gray) # use appropriate colormap here
plt.show()
The resulting image:
The code from the question works fine.
import matplotlib.pyplot as plt
import numpy as np
img = plt.imread("https://i.stack.imgur.com/oos05.png")[88:456,82:326]
t = 0.5
O = (img >= t) * 1
I = img
both = np.hstack((I, O))
plt.imshow(both, cmap='gray')
plt.show()

Python rose chart

i was trying to build a windrose chart. i found this link to the code:
(http://youarealegend.blogspot.no/2008/09/windrose.html)
i get the following error, which points to numpy:
C:\Python27\lib\site-packages\numpy\core\fromnumeric.py:2768: RuntimeWarning: invalid value encountered in rint
return round(decimals, out)
has anyone encountered this before?
here is the code:
from windrose import WindroseAxes
from matplotlib import pyplot as plt
import matplotlib.cm as cm
from numpy.random import random
from numpy import arange
#Create wind speed and direction variables
ws = random(500)*6
wd = random(500)*360
#A quick way to create new windrose axes...
def new_axes():
fig = plt.figure(figsize=(8, 8), dpi=80, facecolor='w', edgecolor='w')
rect = [0.1, 0.1, 0.8, 0.8]
ax = WindroseAxes(fig, rect, axisbg='w')
fig.add_axes(ax)
return ax
#...and adjust the legend box
def set_legend(ax):
l = ax.legend(borderaxespad=-0.10)
plt.setp(l.get_texts(), fontsize=8)
#A stacked histogram with normed (displayed in percent) results :
ax = new_axes()
ax.bar(wd, ws, normed=True, opening=0.8, edgecolor='white')
set_legend(ax)

matplotlib subplot2grid doesn't display correctly

I'm using subplot2grid to display graphs. However, not all subplots are being displayed. Obviously it has to do with the if statement.
However, in my complete code I need those if statements because depending on some conditions plots have diffent formats. I want all 3 subplots to be displayed (one for each i). However, the first one is missing. How to display it correctly?
Here is the simplified code:
import matplotlib.pyplot as plt
fig=plt.figure()
for i in xrange(0,3):
if i==1:
ax=plt.subplot2grid((3,1),(i,0))
ax.plot([1,2],[1,2])
fig.autofmt_xdate()
else:
ax=plt.subplot2grid((3,1),(i,0), rowspan=2)
ax.plot([1,2],[1,2])
fig.autofmt_xdate()
plt.show()
I would just use the gridspec module from matplotlib. Then you can set the width/height ratios directly.
Then you can do something like this:
import numpy
from matplotlib import gridspec
import matplotlib.pyplot as plt
def do_plot_1(ax):
ax.plot([0.25, 0.5, 0.75], [0.25, 0.5, 0.75], 'k-')
def do_plot_2(ax):
ax.plot([0.25, 0.5, 0.75], [0.25, 0.5, 0.75], 'g--')
fig = plt.figure(figsize=(6, 4))
gs = gridspec.GridSpec(nrows=3, ncols=1, height_ratios=[2, 1, 2])
for n in range(3):
ax = fig.add_subplot(gs[n])
if n == 1:
do_plot_1(ax)
else:
do_plot_2(ax)
fig.tight_layout()
To use plt.subplot2grid, you'd need to effectively do something like this:
fig = plt.figure(figsize=(6, 4))
ax1 = plt.subplot2grid((5,1), (0, 0), rowspan=2)
ax2 = plt.subplot2grid((5,1), (2, 0), rowspan=1)
ax3 = plt.subplot2grid((5,1), (3, 0), rowspan=2)
Since you have two axes with a rowspan=2, your grid needs to be 2+1+2 = 5 blocks tall.

Multi-Axis Graph with Line on top. Matplotlib

I'm attempting to make use of twinx() to create a bar/line combo graph with the line visible on top of the bar. Currently this is how it appears:
I also need the line chart to be plotted on the left vertical axis (ax) and the bar on the right (ax2) as it currently is. If I plot the line on the second axis it does appear on top, but obviously it appears on the wrong axis (right)
Here's my code:
self.ax2=ax.twinx()
df[['Opportunities']].plot(kind='bar', stacked=False, title=get_title, color='grey', ax=self.ax2, grid=False)
ax.plot(ax.get_xticks(),df[['Percentage']].values, linestyle='-', marker='o', color='k', linewidth=1.0)
lines, labels = ax.get_legend_handles_labels()
lines2, labels2 = self.ax2.get_legend_handles_labels()
ax.legend(lines + lines2, labels + labels2, loc='lower right')
Also having trouble with the labels, but one thing at a time.
It appears, by default, that the artists are drawn on ax first, then the
artists on the twin axes ax2 on top. So since in your code the line plot was drawn on ax and the bar plot on ax2, the bar plot sits on top of (and obscures) the line.
(I thought I could change this by specifying zorder, but that attempt did not
work... )
So one way to solve the problem is to use ax to draw the bar plot and ax2 to draw the line. That will place the line on top of the bars. It will also, by default, place the ytick labels for ax (the bar plot) on the left, and the ytick labels for ax2 (the line) on the right. However, you can use
ax.yaxis.set_ticks_position("right")
ax2.yaxis.set_ticks_position("left")
to swap the location of the left and right ytick labels.
import numpy as np
import matplotlib.pyplot as plt
import matplotlib.dates as mdates
import pandas as pd
np.random.seed(2015)
N = 16
df = pd.DataFrame({'Opportunities': np.random.randint(0, 30, size=N),
'Percentage': np.random.randint(0, 100, size=N)},
index=pd.date_range('2015-3-15', periods=N, freq='B').date)
fig, ax = plt.subplots()
df[['Opportunities']].plot(kind='bar', stacked=False, title='get_title',
color='grey', ax=ax, grid=False)
ax2 = ax.twinx()
ax2.plot(ax.get_xticks(), df[['Percentage']].values, linestyle='-', marker='o',
color='k', linewidth=1.0, label='percentage')
lines, labels = ax.get_legend_handles_labels()
lines2, labels2 = ax2.get_legend_handles_labels()
ax.legend(lines + lines2, labels + labels2, loc='best')
ax.yaxis.set_ticks_position("right")
ax2.yaxis.set_ticks_position("left")
fig.autofmt_xdate()
plt.show()
yields
Alternatively, the zorder of the axes can be set so as to draw ax above ax2. Paul Ivanov shows how:
ax.set_zorder(ax2.get_zorder()+1) # put ax in front of ax2
ax.patch.set_visible(False) # hide the 'canvas'
ax2.patch.set_visible(True) # show the 'canvas'
Thus,
import numpy as np
import matplotlib.pyplot as plt
import matplotlib.dates as mdates
import pandas as pd
np.random.seed(2015)
N = 16
df = pd.DataFrame({'Opportunities': np.random.randint(0, 30, size=N),
'Percentage': np.random.randint(0, 100, size=N)},
index=pd.date_range('2015-3-15', periods=N, freq='B').date)
fig, ax = plt.subplots()
ax2 = ax.twinx()
df[['Opportunities']].plot(kind='bar', stacked=False, title='get_title',
color='grey', ax=ax2, grid=False)
ax.plot(ax.get_xticks(), df[['Percentage']].values, linestyle='-', marker='o',
color='k', linewidth=1.0, label='percentage')
lines, labels = ax.get_legend_handles_labels()
lines2, labels2 = ax2.get_legend_handles_labels()
ax.legend(lines + lines2, labels + labels2, loc='best')
ax.set_zorder(ax2.get_zorder()+1) # put ax in front of ax2
ax.patch.set_visible(False) # hide the 'canvas'
ax2.patch.set_visible(True) # show the 'canvas'
fig.autofmt_xdate()
plt.show()
yields the same result without having to swap the roles played by ax and ax2.