mirror of
https://github.com/SheffieldML/GPy.git
synced 2026-05-21 14:05:14 +02:00
[huge merge] trying to merge old master and master
This commit is contained in:
commit
180650ec85
308 changed files with 27071 additions and 24550 deletions
7
GPy/plotting/__init__.py
Normal file
7
GPy/plotting/__init__.py
Normal file
|
|
@ -0,0 +1,7 @@
|
|||
# Copyright (c) 2014, GPy authors (see AUTHORS.txt).
|
||||
# Licensed under the BSD 3-clause license (see LICENSE.txt)
|
||||
|
||||
try:
|
||||
import matplot_dep
|
||||
except (ImportError, NameError):
|
||||
print 'Fail to load GPy.plotting.matplot_dep.'
|
||||
165
GPy/plotting/matplot_dep/Tango.py
Normal file
165
GPy/plotting/matplot_dep/Tango.py
Normal file
|
|
@ -0,0 +1,165 @@
|
|||
# Copyright (c) 2012, GPy authors (see AUTHORS.txt).
|
||||
# Licensed under the BSD 3-clause license (see LICENSE.txt)
|
||||
|
||||
|
||||
#sys.path.append('/home/james/mlprojects/sitran_cluster/')
|
||||
#from switch_pylab_backend import *
|
||||
|
||||
|
||||
#this stuff isn;t really Tango related: maybe it could be moved out? TODO
|
||||
def removeRightTicks(ax=None):
|
||||
ax = ax or pb.gca()
|
||||
for i, line in enumerate(ax.get_yticklines()):
|
||||
if i%2 == 1: # odd indices
|
||||
line.set_visible(False)
|
||||
def removeUpperTicks(ax=None):
|
||||
ax = ax or pb.gca()
|
||||
for i, line in enumerate(ax.get_xticklines()):
|
||||
if i%2 == 1: # odd indices
|
||||
line.set_visible(False)
|
||||
def fewerXticks(ax=None,divideby=2):
|
||||
ax = ax or pb.gca()
|
||||
ax.set_xticks(ax.get_xticks()[::divideby])
|
||||
|
||||
|
||||
colorsHex = {\
|
||||
"Aluminium6":"#2e3436",\
|
||||
"Aluminium5":"#555753",\
|
||||
"Aluminium4":"#888a85",\
|
||||
"Aluminium3":"#babdb6",\
|
||||
"Aluminium2":"#d3d7cf",\
|
||||
"Aluminium1":"#eeeeec",\
|
||||
"lightPurple":"#ad7fa8",\
|
||||
"mediumPurple":"#75507b",\
|
||||
"darkPurple":"#5c3566",\
|
||||
"lightBlue":"#729fcf",\
|
||||
"mediumBlue":"#3465a4",\
|
||||
"darkBlue": "#204a87",\
|
||||
"lightGreen":"#8ae234",\
|
||||
"mediumGreen":"#73d216",\
|
||||
"darkGreen":"#4e9a06",\
|
||||
"lightChocolate":"#e9b96e",\
|
||||
"mediumChocolate":"#c17d11",\
|
||||
"darkChocolate":"#8f5902",\
|
||||
"lightRed":"#ef2929",\
|
||||
"mediumRed":"#cc0000",\
|
||||
"darkRed":"#a40000",\
|
||||
"lightOrange":"#fcaf3e",\
|
||||
"mediumOrange":"#f57900",\
|
||||
"darkOrange":"#ce5c00",\
|
||||
"lightButter":"#fce94f",\
|
||||
"mediumButter":"#edd400",\
|
||||
"darkButter":"#c4a000"}
|
||||
|
||||
darkList = [colorsHex['darkBlue'],colorsHex['darkRed'],colorsHex['darkGreen'], colorsHex['darkOrange'], colorsHex['darkButter'], colorsHex['darkPurple'], colorsHex['darkChocolate'], colorsHex['Aluminium6']]
|
||||
mediumList = [colorsHex['mediumBlue'], colorsHex['mediumRed'],colorsHex['mediumGreen'], colorsHex['mediumOrange'], colorsHex['mediumButter'], colorsHex['mediumPurple'], colorsHex['mediumChocolate'], colorsHex['Aluminium5']]
|
||||
lightList = [colorsHex['lightBlue'], colorsHex['lightRed'],colorsHex['lightGreen'], colorsHex['lightOrange'], colorsHex['lightButter'], colorsHex['lightPurple'], colorsHex['lightChocolate'], colorsHex['Aluminium4']]
|
||||
|
||||
def currentDark():
|
||||
return darkList[-1]
|
||||
def currentMedium():
|
||||
return mediumList[-1]
|
||||
def currentLight():
|
||||
return lightList[-1]
|
||||
|
||||
def nextDark():
|
||||
darkList.append(darkList.pop(0))
|
||||
return darkList[-1]
|
||||
def nextMedium():
|
||||
mediumList.append(mediumList.pop(0))
|
||||
return mediumList[-1]
|
||||
def nextLight():
|
||||
lightList.append(lightList.pop(0))
|
||||
return lightList[-1]
|
||||
|
||||
def reset():
|
||||
while not darkList[0]==colorsHex['darkBlue']:
|
||||
darkList.append(darkList.pop(0))
|
||||
while not mediumList[0]==colorsHex['mediumBlue']:
|
||||
mediumList.append(mediumList.pop(0))
|
||||
while not lightList[0]==colorsHex['lightBlue']:
|
||||
lightList.append(lightList.pop(0))
|
||||
|
||||
def setLightFigures():
|
||||
import matplotlib as mpl
|
||||
mpl.rcParams['axes.edgecolor']=colorsHex['Aluminium6']
|
||||
mpl.rcParams['axes.facecolor']=colorsHex['Aluminium2']
|
||||
mpl.rcParams['axes.labelcolor']=colorsHex['Aluminium6']
|
||||
mpl.rcParams['figure.edgecolor']=colorsHex['Aluminium6']
|
||||
mpl.rcParams['figure.facecolor']=colorsHex['Aluminium2']
|
||||
mpl.rcParams['grid.color']=colorsHex['Aluminium6']
|
||||
mpl.rcParams['savefig.edgecolor']=colorsHex['Aluminium2']
|
||||
mpl.rcParams['savefig.facecolor']=colorsHex['Aluminium2']
|
||||
mpl.rcParams['text.color']=colorsHex['Aluminium6']
|
||||
mpl.rcParams['xtick.color']=colorsHex['Aluminium6']
|
||||
mpl.rcParams['ytick.color']=colorsHex['Aluminium6']
|
||||
|
||||
def setDarkFigures():
|
||||
import matplotlib as mpl
|
||||
mpl.rcParams['axes.edgecolor']=colorsHex['Aluminium2']
|
||||
mpl.rcParams['axes.facecolor']=colorsHex['Aluminium6']
|
||||
mpl.rcParams['axes.labelcolor']=colorsHex['Aluminium2']
|
||||
mpl.rcParams['figure.edgecolor']=colorsHex['Aluminium2']
|
||||
mpl.rcParams['figure.facecolor']=colorsHex['Aluminium6']
|
||||
mpl.rcParams['grid.color']=colorsHex['Aluminium2']
|
||||
mpl.rcParams['savefig.edgecolor']=colorsHex['Aluminium6']
|
||||
mpl.rcParams['savefig.facecolor']=colorsHex['Aluminium6']
|
||||
mpl.rcParams['text.color']=colorsHex['Aluminium2']
|
||||
mpl.rcParams['xtick.color']=colorsHex['Aluminium2']
|
||||
mpl.rcParams['ytick.color']=colorsHex['Aluminium2']
|
||||
|
||||
def hex2rgb(hexcolor):
|
||||
hexcolor = [hexcolor[1+2*i:1+2*(i+1)] for i in range(3)]
|
||||
r,g,b = [int(n,16) for n in hexcolor]
|
||||
return (r,g,b)
|
||||
|
||||
colorsRGB = dict([(k,hex2rgb(i)) for k,i in colorsHex.items()])
|
||||
|
||||
cdict_RB = {'red' :((0.,colorsRGB['mediumRed'][0]/256.,colorsRGB['mediumRed'][0]/256.),
|
||||
(.5,colorsRGB['mediumPurple'][0]/256.,colorsRGB['mediumPurple'][0]/256.),
|
||||
(1.,colorsRGB['mediumBlue'][0]/256.,colorsRGB['mediumBlue'][0]/256.)),
|
||||
'green':((0.,colorsRGB['mediumRed'][1]/256.,colorsRGB['mediumRed'][1]/256.),
|
||||
(.5,colorsRGB['mediumPurple'][1]/256.,colorsRGB['mediumPurple'][1]/256.),
|
||||
(1.,colorsRGB['mediumBlue'][1]/256.,colorsRGB['mediumBlue'][1]/256.)),
|
||||
'blue':((0.,colorsRGB['mediumRed'][2]/256.,colorsRGB['mediumRed'][2]/256.),
|
||||
(.5,colorsRGB['mediumPurple'][2]/256.,colorsRGB['mediumPurple'][2]/256.),
|
||||
(1.,colorsRGB['mediumBlue'][2]/256.,colorsRGB['mediumBlue'][2]/256.))}
|
||||
|
||||
cdict_BGR = {'red' :((0.,colorsRGB['mediumBlue'][0]/256.,colorsRGB['mediumBlue'][0]/256.),
|
||||
(.5,colorsRGB['mediumGreen'][0]/256.,colorsRGB['mediumGreen'][0]/256.),
|
||||
(1.,colorsRGB['mediumRed'][0]/256.,colorsRGB['mediumRed'][0]/256.)),
|
||||
'green':((0.,colorsRGB['mediumBlue'][1]/256.,colorsRGB['mediumBlue'][1]/256.),
|
||||
(.5,colorsRGB['mediumGreen'][1]/256.,colorsRGB['mediumGreen'][1]/256.),
|
||||
(1.,colorsRGB['mediumRed'][1]/256.,colorsRGB['mediumRed'][1]/256.)),
|
||||
'blue':((0.,colorsRGB['mediumBlue'][2]/256.,colorsRGB['mediumBlue'][2]/256.),
|
||||
(.5,colorsRGB['mediumGreen'][2]/256.,colorsRGB['mediumGreen'][2]/256.),
|
||||
(1.,colorsRGB['mediumRed'][2]/256.,colorsRGB['mediumRed'][2]/256.))}
|
||||
|
||||
|
||||
cdict_Alu = {'red' :((0./5,colorsRGB['Aluminium1'][0]/256.,colorsRGB['Aluminium1'][0]/256.),
|
||||
(1./5,colorsRGB['Aluminium2'][0]/256.,colorsRGB['Aluminium2'][0]/256.),
|
||||
(2./5,colorsRGB['Aluminium3'][0]/256.,colorsRGB['Aluminium3'][0]/256.),
|
||||
(3./5,colorsRGB['Aluminium4'][0]/256.,colorsRGB['Aluminium4'][0]/256.),
|
||||
(4./5,colorsRGB['Aluminium5'][0]/256.,colorsRGB['Aluminium5'][0]/256.),
|
||||
(5./5,colorsRGB['Aluminium6'][0]/256.,colorsRGB['Aluminium6'][0]/256.)),
|
||||
'green' :((0./5,colorsRGB['Aluminium1'][1]/256.,colorsRGB['Aluminium1'][1]/256.),
|
||||
(1./5,colorsRGB['Aluminium2'][1]/256.,colorsRGB['Aluminium2'][1]/256.),
|
||||
(2./5,colorsRGB['Aluminium3'][1]/256.,colorsRGB['Aluminium3'][1]/256.),
|
||||
(3./5,colorsRGB['Aluminium4'][1]/256.,colorsRGB['Aluminium4'][1]/256.),
|
||||
(4./5,colorsRGB['Aluminium5'][1]/256.,colorsRGB['Aluminium5'][1]/256.),
|
||||
(5./5,colorsRGB['Aluminium6'][1]/256.,colorsRGB['Aluminium6'][1]/256.)),
|
||||
'blue' :((0./5,colorsRGB['Aluminium1'][2]/256.,colorsRGB['Aluminium1'][2]/256.),
|
||||
(1./5,colorsRGB['Aluminium2'][2]/256.,colorsRGB['Aluminium2'][2]/256.),
|
||||
(2./5,colorsRGB['Aluminium3'][2]/256.,colorsRGB['Aluminium3'][2]/256.),
|
||||
(3./5,colorsRGB['Aluminium4'][2]/256.,colorsRGB['Aluminium4'][2]/256.),
|
||||
(4./5,colorsRGB['Aluminium5'][2]/256.,colorsRGB['Aluminium5'][2]/256.),
|
||||
(5./5,colorsRGB['Aluminium6'][2]/256.,colorsRGB['Aluminium6'][2]/256.))}
|
||||
# cmap_Alu = mpl.colors.LinearSegmentedColormap('TangoAluminium',cdict_Alu,256)
|
||||
# cmap_BGR = mpl.colors.LinearSegmentedColormap('TangoRedBlue',cdict_BGR,256)
|
||||
if __name__=='__main__':
|
||||
import matplotlib.pyplot as pb, numpy as np
|
||||
pb.figure()
|
||||
cmap_RB = mpl.colors.LinearSegmentedColormap('TangoRedBlue',cdict_RB,256)
|
||||
pb.pcolor(np.random.rand(10,10),cmap=cmap_RB)
|
||||
pb.colorbar()
|
||||
pb.show()
|
||||
18
GPy/plotting/matplot_dep/__init__.py
Normal file
18
GPy/plotting/matplot_dep/__init__.py
Normal file
|
|
@ -0,0 +1,18 @@
|
|||
# Copyright (c) 2014, GPy authors (see AUTHORS.txt).
|
||||
# Licensed under the BSD 3-clause license (see LICENSE.txt)
|
||||
|
||||
import base_plots
|
||||
import models_plots
|
||||
import priors_plots
|
||||
import variational_plots
|
||||
import kernel_plots
|
||||
import dim_reduction_plots
|
||||
import mapping_plots
|
||||
import Tango
|
||||
import visualize
|
||||
import latent_space_visualizations
|
||||
import netpbmfile
|
||||
import inference_plots
|
||||
import maps
|
||||
import img_plots
|
||||
from ssgplvm import SSGPLVM_plot
|
||||
157
GPy/plotting/matplot_dep/base_plots.py
Normal file
157
GPy/plotting/matplot_dep/base_plots.py
Normal file
|
|
@ -0,0 +1,157 @@
|
|||
# #Copyright (c) 2012, GPy authors (see AUTHORS.txt).
|
||||
# Licensed under the BSD 3-clause license (see LICENSE.txt)
|
||||
|
||||
|
||||
try:
|
||||
import Tango
|
||||
import pylab as pb
|
||||
except:
|
||||
pass
|
||||
import numpy as np
|
||||
|
||||
def ax_default(fignum, ax):
|
||||
if ax is None:
|
||||
fig = pb.figure(fignum)
|
||||
ax = fig.add_subplot(111)
|
||||
else:
|
||||
fig = ax.figure
|
||||
return fig, ax
|
||||
|
||||
def meanplot(x, mu, color=Tango.colorsHex['darkBlue'], ax=None, fignum=None, linewidth=2,**kw):
|
||||
_, axes = ax_default(fignum, ax)
|
||||
return axes.plot(x,mu,color=color,linewidth=linewidth,**kw)
|
||||
|
||||
def gpplot(x, mu, lower, upper, edgecol=Tango.colorsHex['darkBlue'], fillcol=Tango.colorsHex['lightBlue'], ax=None, fignum=None, **kwargs):
|
||||
_, axes = ax_default(fignum, ax)
|
||||
|
||||
mu = mu.flatten()
|
||||
x = x.flatten()
|
||||
lower = lower.flatten()
|
||||
upper = upper.flatten()
|
||||
|
||||
plots = []
|
||||
|
||||
#here's the mean
|
||||
plots.append(meanplot(x, mu, edgecol, axes))
|
||||
|
||||
#here's the box
|
||||
kwargs['linewidth']=0.5
|
||||
if not 'alpha' in kwargs.keys():
|
||||
kwargs['alpha'] = 0.3
|
||||
plots.append(axes.fill(np.hstack((x,x[::-1])),np.hstack((upper,lower[::-1])),color=fillcol,**kwargs))
|
||||
|
||||
#this is the edge:
|
||||
plots.append(meanplot(x, upper,color=edgecol,linewidth=0.2,ax=axes))
|
||||
plots.append(meanplot(x, lower,color=edgecol,linewidth=0.2,ax=axes))
|
||||
|
||||
return plots
|
||||
|
||||
|
||||
def removeRightTicks(ax=None):
|
||||
ax = ax or pb.gca()
|
||||
for i, line in enumerate(ax.get_yticklines()):
|
||||
if i%2 == 1: # odd indices
|
||||
line.set_visible(False)
|
||||
|
||||
def removeUpperTicks(ax=None):
|
||||
ax = ax or pb.gca()
|
||||
for i, line in enumerate(ax.get_xticklines()):
|
||||
if i%2 == 1: # odd indices
|
||||
line.set_visible(False)
|
||||
|
||||
def fewerXticks(ax=None,divideby=2):
|
||||
ax = ax or pb.gca()
|
||||
ax.set_xticks(ax.get_xticks()[::divideby])
|
||||
|
||||
def align_subplots(N,M,xlim=None, ylim=None):
|
||||
"""make all of the subplots have the same limits, turn off unnecessary ticks"""
|
||||
#find sensible xlim,ylim
|
||||
if xlim is None:
|
||||
xlim = [np.inf,-np.inf]
|
||||
for i in range(N*M):
|
||||
pb.subplot(N,M,i+1)
|
||||
xlim[0] = min(xlim[0],pb.xlim()[0])
|
||||
xlim[1] = max(xlim[1],pb.xlim()[1])
|
||||
if ylim is None:
|
||||
ylim = [np.inf,-np.inf]
|
||||
for i in range(N*M):
|
||||
pb.subplot(N,M,i+1)
|
||||
ylim[0] = min(ylim[0],pb.ylim()[0])
|
||||
ylim[1] = max(ylim[1],pb.ylim()[1])
|
||||
|
||||
for i in range(N*M):
|
||||
pb.subplot(N,M,i+1)
|
||||
pb.xlim(xlim)
|
||||
pb.ylim(ylim)
|
||||
if (i)%M:
|
||||
pb.yticks([])
|
||||
else:
|
||||
removeRightTicks()
|
||||
if i<(M*(N-1)):
|
||||
pb.xticks([])
|
||||
else:
|
||||
removeUpperTicks()
|
||||
|
||||
def align_subplot_array(axes,xlim=None, ylim=None):
|
||||
"""
|
||||
Make all of the axes in the array hae the same limits, turn off unnecessary ticks
|
||||
use pb.subplots() to get an array of axes
|
||||
"""
|
||||
#find sensible xlim,ylim
|
||||
if xlim is None:
|
||||
xlim = [np.inf,-np.inf]
|
||||
for ax in axes.flatten():
|
||||
xlim[0] = min(xlim[0],ax.get_xlim()[0])
|
||||
xlim[1] = max(xlim[1],ax.get_xlim()[1])
|
||||
if ylim is None:
|
||||
ylim = [np.inf,-np.inf]
|
||||
for ax in axes.flatten():
|
||||
ylim[0] = min(ylim[0],ax.get_ylim()[0])
|
||||
ylim[1] = max(ylim[1],ax.get_ylim()[1])
|
||||
|
||||
N,M = axes.shape
|
||||
for i,ax in enumerate(axes.flatten()):
|
||||
ax.set_xlim(xlim)
|
||||
ax.set_ylim(ylim)
|
||||
if (i)%M:
|
||||
ax.set_yticks([])
|
||||
else:
|
||||
removeRightTicks(ax)
|
||||
if i<(M*(N-1)):
|
||||
ax.set_xticks([])
|
||||
else:
|
||||
removeUpperTicks(ax)
|
||||
|
||||
def x_frame1D(X,plot_limits=None,resolution=None):
|
||||
"""
|
||||
Internal helper function for making plots, returns a set of input values to plot as well as lower and upper limits
|
||||
"""
|
||||
assert X.shape[1] ==1, "x_frame1D is defined for one-dimensional inputs"
|
||||
if plot_limits is None:
|
||||
xmin,xmax = X.min(0),X.max(0)
|
||||
xmin, xmax = xmin-0.2*(xmax-xmin), xmax+0.2*(xmax-xmin)
|
||||
elif len(plot_limits)==2:
|
||||
xmin, xmax = plot_limits
|
||||
else:
|
||||
raise ValueError, "Bad limits for plotting"
|
||||
|
||||
Xnew = np.linspace(xmin,xmax,resolution or 200)[:,None]
|
||||
return Xnew, xmin, xmax
|
||||
|
||||
def x_frame2D(X,plot_limits=None,resolution=None):
|
||||
"""
|
||||
Internal helper function for making plots, returns a set of input values to plot as well as lower and upper limits
|
||||
"""
|
||||
assert X.shape[1] ==2, "x_frame2D is defined for two-dimensional inputs"
|
||||
if plot_limits is None:
|
||||
xmin,xmax = X.min(0),X.max(0)
|
||||
xmin, xmax = xmin-0.2*(xmax-xmin), xmax+0.2*(xmax-xmin)
|
||||
elif len(plot_limits)==2:
|
||||
xmin, xmax = plot_limits
|
||||
else:
|
||||
raise ValueError, "Bad limits for plotting"
|
||||
|
||||
resolution = resolution or 50
|
||||
xx,yy = np.mgrid[xmin[0]:xmax[0]:1j*resolution,xmin[1]:xmax[1]:1j*resolution]
|
||||
Xnew = np.vstack((xx.flatten(),yy.flatten())).T
|
||||
return Xnew, xx, yy, xmin, xmax
|
||||
338
GPy/plotting/matplot_dep/dim_reduction_plots.py
Normal file
338
GPy/plotting/matplot_dep/dim_reduction_plots.py
Normal file
|
|
@ -0,0 +1,338 @@
|
|||
# Copyright (c) 2012, GPy authors (see AUTHORS.txt).
|
||||
# Licensed under the BSD 3-clause license (see LICENSE.txt)
|
||||
|
||||
import numpy as np
|
||||
from latent_space_visualizations.controllers.imshow_controller import ImshowController,ImAnnotateController
|
||||
from ...core.parameterization.variational import VariationalPosterior
|
||||
from .base_plots import x_frame2D
|
||||
import itertools
|
||||
try:
|
||||
import Tango
|
||||
from matplotlib.cm import get_cmap
|
||||
import pylab as pb
|
||||
except:
|
||||
pass
|
||||
|
||||
def most_significant_input_dimensions(model, which_indices):
|
||||
"""
|
||||
Determine which dimensions should be plotted
|
||||
"""
|
||||
if which_indices is None:
|
||||
if model.input_dim == 1:
|
||||
input_1 = 0
|
||||
input_2 = None
|
||||
if model.input_dim == 2:
|
||||
input_1, input_2 = 0, 1
|
||||
else:
|
||||
try:
|
||||
input_1, input_2 = np.argsort(model.input_sensitivity())[::-1][:2]
|
||||
except:
|
||||
raise ValueError, "cannot automatically determine which dimensions to plot, please pass 'which_indices'"
|
||||
else:
|
||||
input_1, input_2 = which_indices
|
||||
return input_1, input_2
|
||||
|
||||
def plot_latent(model, labels=None, which_indices=None,
|
||||
resolution=50, ax=None, marker='o', s=40,
|
||||
fignum=None, plot_inducing=False, legend=True,
|
||||
plot_limits=None,
|
||||
aspect='auto', updates=False, predict_kwargs={}, imshow_kwargs={}):
|
||||
"""
|
||||
:param labels: a np.array of size model.num_data containing labels for the points (can be number, strings, etc)
|
||||
:param resolution: the resolution of the grid on which to evaluate the predictive variance
|
||||
"""
|
||||
if ax is None:
|
||||
fig = pb.figure(num=fignum)
|
||||
ax = fig.add_subplot(111)
|
||||
else:
|
||||
fig = ax.figure
|
||||
Tango.reset()
|
||||
|
||||
if labels is None:
|
||||
labels = np.ones(model.num_data)
|
||||
|
||||
input_1, input_2 = most_significant_input_dimensions(model, which_indices)
|
||||
|
||||
#fethch the data points X that we'd like to plot
|
||||
X = model.X
|
||||
if isinstance(X, VariationalPosterior):
|
||||
X = X.mean
|
||||
else:
|
||||
X = X
|
||||
|
||||
|
||||
if X.shape[0] > 1000:
|
||||
print "Warning: subsampling X, as it has more samples then 1000. X.shape={!s}".format(X.shape)
|
||||
subsample = np.random.choice(X.shape[0], size=1000, replace=False)
|
||||
X = X[subsample]
|
||||
labels = labels[subsample]
|
||||
#=======================================================================
|
||||
# <<<WORK IN PROGRESS>>>
|
||||
# <<<DO NOT DELETE>>>
|
||||
# plt.close('all')
|
||||
# fig, ax = plt.subplots(1,1)
|
||||
# from GPy.plotting.matplot_dep.dim_reduction_plots import most_significant_input_dimensions
|
||||
# import matplotlib.patches as mpatches
|
||||
# i1, i2 = most_significant_input_dimensions(m, None)
|
||||
# xmin, xmax = 100, -100
|
||||
# ymin, ymax = 100, -100
|
||||
# legend_handles = []
|
||||
#
|
||||
# X = m.X.mean[:, [i1, i2]]
|
||||
# X = m.X.variance[:, [i1, i2]]
|
||||
#
|
||||
# xmin = X[:,0].min(); xmax = X[:,0].max()
|
||||
# ymin = X[:,1].min(); ymax = X[:,1].max()
|
||||
# range_ = [[xmin, xmax], [ymin, ymax]]
|
||||
# ul = np.unique(labels)
|
||||
#
|
||||
# for i, l in enumerate(ul):
|
||||
# #cdict = dict(red =[(0., colors[i][0], colors[i][0]), (1., colors[i][0], colors[i][0])],
|
||||
# # green=[(0., colors[i][0], colors[i][1]), (1., colors[i][1], colors[i][1])],
|
||||
# # blue =[(0., colors[i][0], colors[i][2]), (1., colors[i][2], colors[i][2])],
|
||||
# # alpha=[(0., 0., .0), (.5, .5, .5), (1., .5, .5)])
|
||||
# #cmap = LinearSegmentedColormap('{}'.format(l), cdict)
|
||||
# cmap = LinearSegmentedColormap.from_list('cmap_{}'.format(str(l)), [colors[i], colors[i]], 255)
|
||||
# cmap._init()
|
||||
# #alphas = .5*(1+scipy.special.erf(np.linspace(-2,2, cmap.N+3)))#np.log(np.linspace(np.exp(0), np.exp(1.), cmap.N+3))
|
||||
# alphas = (scipy.special.erf(np.linspace(0,2.4, cmap.N+3)))#np.log(np.linspace(np.exp(0), np.exp(1.), cmap.N+3))
|
||||
# cmap._lut[:, -1] = alphas
|
||||
# print l
|
||||
# x, y = X[labels==l].T
|
||||
#
|
||||
# heatmap, xedges, yedges = np.histogram2d(x, y, bins=300, range=range_)
|
||||
# #heatmap, xedges, yedges = np.histogram2d(x, y, bins=100)
|
||||
#
|
||||
# im = ax.imshow(heatmap, extent=[xedges[0], xedges[-1], yedges[0], yedges[-1]], cmap=cmap, aspect='auto', interpolation='nearest', label=str(l))
|
||||
# legend_handles.append(mpatches.Patch(color=colors[i], label=l))
|
||||
# ax.set_xlim(xmin, xmax)
|
||||
# ax.set_ylim(ymin, ymax)
|
||||
# plt.legend(legend_handles, [l.get_label() for l in legend_handles])
|
||||
# plt.draw()
|
||||
# plt.show()
|
||||
#=======================================================================
|
||||
|
||||
# create a function which computes the shading of latent space according to the output variance
|
||||
def plot_function(x):
|
||||
Xtest_full = np.zeros((x.shape[0], model.X.shape[1]))
|
||||
Xtest_full[:, [input_1, input_2]] = x
|
||||
_, var = model.predict(Xtest_full, **predict_kwargs)
|
||||
var = var[:, :1]
|
||||
return np.log(var)
|
||||
|
||||
#Create an IMshow controller that can re-plot the latent space shading at a good resolution
|
||||
if plot_limits is None:
|
||||
xmin, ymin = X[:, [input_1, input_2]].min(0)
|
||||
xmax, ymax = X[:, [input_1, input_2]].max(0)
|
||||
x_r, y_r = xmax-xmin, ymax-ymin
|
||||
xmin -= .1*x_r
|
||||
xmax += .1*x_r
|
||||
ymin -= .1*y_r
|
||||
ymax += .1*y_r
|
||||
else:
|
||||
try:
|
||||
xmin, xmax, ymin, ymax = plot_limits
|
||||
except (TypeError, ValueError) as e:
|
||||
raise e.__class__, "Wrong plot limits: {} given -> need (xmin, xmax, ymin, ymax)".format(plot_limits)
|
||||
view = ImshowController(ax, plot_function,
|
||||
(xmin, ymin, xmax, ymax),
|
||||
resolution, aspect=aspect, interpolation='bilinear',
|
||||
cmap=pb.cm.binary, **imshow_kwargs)
|
||||
|
||||
# make sure labels are in order of input:
|
||||
labels = np.asarray(labels)
|
||||
ulabels = []
|
||||
for lab in labels:
|
||||
if not lab in ulabels:
|
||||
ulabels.append(lab)
|
||||
|
||||
marker = itertools.cycle(list(marker))
|
||||
|
||||
for i, ul in enumerate(ulabels):
|
||||
if type(ul) is np.string_:
|
||||
this_label = ul
|
||||
elif type(ul) is np.int64:
|
||||
this_label = 'class %i' % ul
|
||||
else:
|
||||
this_label = unicode(ul)
|
||||
m = marker.next()
|
||||
|
||||
index = np.nonzero(labels == ul)[0]
|
||||
if model.input_dim == 1:
|
||||
x = X[index, input_1]
|
||||
y = np.zeros(index.size)
|
||||
else:
|
||||
x = X[index, input_1]
|
||||
y = X[index, input_2]
|
||||
ax.scatter(x, y, marker=m, s=s, c=Tango.nextMedium(), label=this_label, linewidth=.2, edgecolor='k', alpha=.9)
|
||||
|
||||
ax.set_xlabel('latent dimension %i' % input_1)
|
||||
ax.set_ylabel('latent dimension %i' % input_2)
|
||||
|
||||
if not np.all(labels == 1.) and legend:
|
||||
ax.legend(loc=0, numpoints=1)
|
||||
|
||||
ax.grid(b=False) # remove the grid if present, it doesn't look good
|
||||
ax.set_aspect('auto') # set a nice aspect ratio
|
||||
|
||||
if plot_inducing:
|
||||
Z = model.Z
|
||||
ax.scatter(Z[:, input_1], Z[:, input_2], c='w', s=14, marker="^", edgecolor='k', linewidth=.3, alpha=.6)
|
||||
|
||||
ax.set_xlim((xmin, xmax))
|
||||
ax.set_ylim((ymin, ymax))
|
||||
|
||||
try:
|
||||
fig.canvas.draw()
|
||||
fig.tight_layout()
|
||||
fig.canvas.draw()
|
||||
except Exception as e:
|
||||
print "Could not invoke tight layout: {}".format(e)
|
||||
pass
|
||||
|
||||
if updates:
|
||||
try:
|
||||
ax.figure.canvas.show()
|
||||
except Exception as e:
|
||||
print "Could not invoke show: {}".format(e)
|
||||
raw_input('Enter to continue')
|
||||
view.deactivate()
|
||||
return ax
|
||||
|
||||
def plot_magnification(model, labels=None, which_indices=None,
|
||||
resolution=60, ax=None, marker='o', s=40,
|
||||
fignum=None, plot_inducing=False, legend=True,
|
||||
aspect='auto', updates=False):
|
||||
"""
|
||||
:param labels: a np.array of size model.num_data containing labels for the points (can be number, strings, etc)
|
||||
:param resolution: the resolution of the grid on which to evaluate the predictive variance
|
||||
"""
|
||||
if ax is None:
|
||||
fig = pb.figure(num=fignum)
|
||||
ax = fig.add_subplot(111)
|
||||
Tango.reset()
|
||||
|
||||
if labels is None:
|
||||
labels = np.ones(model.num_data)
|
||||
|
||||
input_1, input_2 = most_significant_input_dimensions(model, which_indices)
|
||||
|
||||
# first, plot the output variance as a function of the latent space
|
||||
Xtest, xx, yy, xmin, xmax = x_frame2D(model.X[:, [input_1, input_2]], resolution=resolution)
|
||||
Xtest_full = np.zeros((Xtest.shape[0], model.X.shape[1]))
|
||||
|
||||
def plot_function(x):
|
||||
Xtest_full[:, [input_1, input_2]] = x
|
||||
mf=model.magnification(Xtest_full)
|
||||
return mf
|
||||
|
||||
view = ImshowController(ax, plot_function,
|
||||
tuple(model.X.min(0)[:, [input_1, input_2]]) + tuple(model.X.max(0)[:, [input_1, input_2]]),
|
||||
resolution, aspect=aspect, interpolation='bilinear',
|
||||
cmap=pb.cm.gray)
|
||||
|
||||
# make sure labels are in order of input:
|
||||
ulabels = []
|
||||
for lab in labels:
|
||||
if not lab in ulabels:
|
||||
ulabels.append(lab)
|
||||
|
||||
marker = itertools.cycle(list(marker))
|
||||
|
||||
for i, ul in enumerate(ulabels):
|
||||
if type(ul) is np.string_:
|
||||
this_label = ul
|
||||
elif type(ul) is np.int64:
|
||||
this_label = 'class %i' % ul
|
||||
else:
|
||||
this_label = 'class %i' % i
|
||||
m = marker.next()
|
||||
|
||||
index = np.nonzero(labels == ul)[0]
|
||||
if model.input_dim == 1:
|
||||
x = model.X[index, input_1]
|
||||
y = np.zeros(index.size)
|
||||
else:
|
||||
x = model.X[index, input_1]
|
||||
y = model.X[index, input_2]
|
||||
ax.scatter(x, y, marker=m, s=s, color=Tango.nextMedium(), label=this_label)
|
||||
|
||||
ax.set_xlabel('latent dimension %i' % input_1)
|
||||
ax.set_ylabel('latent dimension %i' % input_2)
|
||||
|
||||
if not np.all(labels == 1.) and legend:
|
||||
ax.legend(loc=0, numpoints=1)
|
||||
|
||||
ax.set_xlim(xmin[0], xmax[0])
|
||||
ax.set_ylim(xmin[1], xmax[1])
|
||||
ax.grid(b=False) # remove the grid if present, it doesn't look good
|
||||
ax.set_aspect('auto') # set a nice aspect ratio
|
||||
|
||||
if plot_inducing:
|
||||
ax.plot(model.Z[:, input_1], model.Z[:, input_2], '^w')
|
||||
|
||||
if updates:
|
||||
fig.canvas.show()
|
||||
raw_input('Enter to continue')
|
||||
|
||||
pb.title('Magnification Factor')
|
||||
return ax
|
||||
|
||||
|
||||
def plot_steepest_gradient_map(model, fignum=None, ax=None, which_indices=None, labels=None, data_labels=None, data_marker='o', data_s=40, resolution=20, aspect='auto', updates=False, ** kwargs):
|
||||
|
||||
input_1, input_2 = significant_dims = most_significant_input_dimensions(model, which_indices)
|
||||
|
||||
X = np.zeros((resolution ** 2, model.input_dim))
|
||||
indices = np.r_[:X.shape[0]]
|
||||
if labels is None:
|
||||
labels = range(model.output_dim)
|
||||
|
||||
def plot_function(x):
|
||||
X[:, significant_dims] = x
|
||||
dmu_dX = model.dmu_dXnew(X)
|
||||
argmax = np.argmax(dmu_dX, 1)
|
||||
return dmu_dX[indices, argmax], np.array(labels)[argmax]
|
||||
|
||||
if ax is None:
|
||||
fig = pb.figure(num=fignum)
|
||||
ax = fig.add_subplot(111)
|
||||
|
||||
if data_labels is None:
|
||||
data_labels = np.ones(model.num_data)
|
||||
ulabels = []
|
||||
for lab in data_labels:
|
||||
if not lab in ulabels:
|
||||
ulabels.append(lab)
|
||||
marker = itertools.cycle(list(data_marker))
|
||||
for i, ul in enumerate(ulabels):
|
||||
if type(ul) is np.string_:
|
||||
this_label = ul
|
||||
elif type(ul) is np.int64:
|
||||
this_label = 'class %i' % ul
|
||||
else:
|
||||
this_label = 'class %i' % i
|
||||
m = marker.next()
|
||||
index = np.nonzero(data_labels == ul)[0]
|
||||
x = model.X[index, input_1]
|
||||
y = model.X[index, input_2]
|
||||
ax.scatter(x, y, marker=m, s=data_s, color=Tango.nextMedium(), label=this_label)
|
||||
|
||||
ax.set_xlabel('latent dimension %i' % input_1)
|
||||
ax.set_ylabel('latent dimension %i' % input_2)
|
||||
|
||||
controller = ImAnnotateController(ax,
|
||||
plot_function,
|
||||
tuple(model.X.min(0)[:, significant_dims]) + tuple(model.X.max(0)[:, significant_dims]),
|
||||
resolution=resolution,
|
||||
aspect=aspect,
|
||||
cmap=get_cmap('jet'),
|
||||
**kwargs)
|
||||
ax.legend()
|
||||
ax.figure.tight_layout()
|
||||
if updates:
|
||||
pb.show()
|
||||
clear = raw_input('Enter to continue')
|
||||
if clear.lower() in 'yes' or clear == '':
|
||||
controller.deactivate()
|
||||
return controller.view
|
||||
58
GPy/plotting/matplot_dep/img_plots.py
Normal file
58
GPy/plotting/matplot_dep/img_plots.py
Normal file
|
|
@ -0,0 +1,58 @@
|
|||
# Copyright (c) 2012, GPy authors (see AUTHORS.txt).
|
||||
# Licensed under the BSD 3-clause license (see LICENSE.txt)
|
||||
"""
|
||||
The module contains the tools for ploting 2D image visualizations
|
||||
"""
|
||||
|
||||
import numpy as np
|
||||
from matplotlib.cm import jet
|
||||
|
||||
width_max = 15
|
||||
height_max = 12
|
||||
|
||||
def _calculateFigureSize(x_size, y_size, fig_ncols, fig_nrows, pad):
|
||||
width = (x_size*fig_ncols+pad*(fig_ncols-1))
|
||||
height = (y_size*fig_nrows+pad*(fig_nrows-1))
|
||||
if width > float(height)/height_max*width_max:
|
||||
return (width_max, float(width_max)/width*height)
|
||||
else:
|
||||
return (float(height_max)/height*width, height_max)
|
||||
|
||||
def plot_2D_images(figure, arr, symmetric=False, pad=None, zoom=None, mode=None, interpolation='nearest'):
|
||||
ax = figure.add_subplot(111)
|
||||
if len(arr.shape)==2:
|
||||
arr = arr.reshape(*((1,)+arr.shape))
|
||||
fig_num = arr.shape[0]
|
||||
y_size = arr.shape[1]
|
||||
x_size = arr.shape[2]
|
||||
fig_ncols = int(np.ceil(np.sqrt(fig_num)))
|
||||
fig_nrows = int(np.ceil((float)(fig_num)/fig_ncols))
|
||||
if pad==None:
|
||||
pad = max(int(min(y_size,x_size)/10),1)
|
||||
|
||||
figsize = _calculateFigureSize(x_size, y_size, fig_ncols, fig_nrows, pad)
|
||||
#figure.set_size_inches(figsize,forward=True)
|
||||
#figure.subplots_adjust(left=0.05, bottom=0.05, right=0.95, top=0.95)
|
||||
|
||||
if symmetric:
|
||||
# symmetric around zero: fix zero as the middle color
|
||||
mval = max(abs(arr.max()),abs(arr.min()))
|
||||
arr = arr/(2.*mval)+0.5
|
||||
else:
|
||||
minval,maxval = arr.min(),arr.max()
|
||||
arr = (arr-minval)/(maxval-minval)
|
||||
|
||||
if mode=='L':
|
||||
arr_color = np.empty(arr.shape+(3,))
|
||||
arr_color[:] = arr.reshape(*(arr.shape+(1,)))
|
||||
elif mode==None or mode=='jet':
|
||||
arr_color = jet(arr)
|
||||
|
||||
buf = np.ones((y_size*fig_nrows+pad*(fig_nrows-1), x_size*fig_ncols+pad*(fig_ncols-1), 3),dtype=arr.dtype)
|
||||
|
||||
for y in xrange(fig_nrows):
|
||||
for x in xrange(fig_ncols):
|
||||
if y*fig_ncols+x<fig_num:
|
||||
buf[y*y_size+y*pad:(y+1)*y_size+y*pad, x*x_size+x*pad:(x+1)*x_size+x*pad] = arr_color[y*fig_ncols+x,:,:,:3]
|
||||
img_plot = ax.imshow(buf, interpolation=interpolation)
|
||||
ax.axis('off')
|
||||
31
GPy/plotting/matplot_dep/inference_plots.py
Normal file
31
GPy/plotting/matplot_dep/inference_plots.py
Normal file
|
|
@ -0,0 +1,31 @@
|
|||
# Copyright (c) 2012, GPy authors (see AUTHORS.txt).
|
||||
# Licensed under the BSD 3-clause license (see LICENSE.txt)
|
||||
|
||||
try:
|
||||
import pylab as pb
|
||||
except:
|
||||
pass
|
||||
#import numpy as np
|
||||
#import Tango
|
||||
#from base_plots import gpplot, x_frame1D, x_frame2D
|
||||
|
||||
|
||||
def plot_optimizer(optimizer):
|
||||
if optimizer.trace == None:
|
||||
print "No trace present so I can't plot it. Please check that the optimizer actually supplies a trace."
|
||||
else:
|
||||
pb.figure()
|
||||
pb.plot(optimizer.trace)
|
||||
pb.xlabel('Iteration')
|
||||
pb.ylabel('f(x)')
|
||||
|
||||
def plot_sgd_traces(optimizer):
|
||||
pb.figure()
|
||||
pb.subplot(211)
|
||||
pb.title('Parameters')
|
||||
for k in optimizer.param_traces.keys():
|
||||
pb.plot(optimizer.param_traces[k], label=k)
|
||||
pb.legend(loc=0)
|
||||
pb.subplot(212)
|
||||
pb.title('Objective function')
|
||||
pb.plot(optimizer.fopt_trace)
|
||||
171
GPy/plotting/matplot_dep/kernel_plots.py
Normal file
171
GPy/plotting/matplot_dep/kernel_plots.py
Normal file
|
|
@ -0,0 +1,171 @@
|
|||
# Copyright (c) 2012, GPy authors (see AUTHORS.txt).
|
||||
# Licensed under the BSD 3-clause license (see LICENSE.txt)
|
||||
|
||||
import numpy as np
|
||||
import pylab as pb
|
||||
import Tango
|
||||
from matplotlib.textpath import TextPath
|
||||
from matplotlib.transforms import offset_copy
|
||||
from .base_plots import ax_default
|
||||
|
||||
|
||||
|
||||
def add_bar_labels(fig, ax, bars, bottom=0):
|
||||
transOffset = offset_copy(ax.transData, fig=fig,
|
||||
x=0., y= -2., units='points')
|
||||
transOffsetUp = offset_copy(ax.transData, fig=fig,
|
||||
x=0., y=1., units='points')
|
||||
for bar in bars:
|
||||
for i, [patch, num] in enumerate(zip(bar.patches, np.arange(len(bar.patches)))):
|
||||
if len(bottom) == len(bar): b = bottom[i]
|
||||
else: b = bottom
|
||||
height = patch.get_height() + b
|
||||
xi = patch.get_x() + patch.get_width() / 2.
|
||||
va = 'top'
|
||||
c = 'w'
|
||||
t = TextPath((0, 0), "${xi}$".format(xi=xi), rotation=0, ha='center')
|
||||
transform = transOffset
|
||||
if patch.get_extents().height <= t.get_extents().height + 5:
|
||||
va = 'bottom'
|
||||
c = 'k'
|
||||
transform = transOffsetUp
|
||||
ax.text(xi, height, "${xi}$".format(xi=int(num)), color=c, rotation=0, ha='center', va=va, transform=transform)
|
||||
|
||||
ax.set_xticks([])
|
||||
|
||||
|
||||
def plot_bars(fig, ax, x, ard_params, color, name, bottom=0):
|
||||
return ax.bar(left=x, height=ard_params.view(np.ndarray), width=.8,
|
||||
bottom=bottom, align='center',
|
||||
color=color, edgecolor='k', linewidth=1.2,
|
||||
label=name.replace("_"," "))
|
||||
|
||||
def plot_ARD(kernel, fignum=None, ax=None, title='', legend=False, filtering=None):
|
||||
"""
|
||||
If an ARD kernel is present, plot a bar representation using matplotlib
|
||||
|
||||
:param fignum: figure number of the plot
|
||||
:param ax: matplotlib axis to plot on
|
||||
:param title:
|
||||
title of the plot,
|
||||
pass '' to not print a title
|
||||
pass None for a generic title
|
||||
:param filtering: list of names, which to use for plotting ARD parameters.
|
||||
Only kernels which match names in the list of names in filtering
|
||||
will be used for plotting.
|
||||
:type filtering: list of names to use for ARD plot
|
||||
"""
|
||||
fig, ax = ax_default(fignum,ax)
|
||||
|
||||
if title is None:
|
||||
ax.set_title('ARD parameters, %s kernel' % kernel.name)
|
||||
else:
|
||||
ax.set_title(title)
|
||||
|
||||
Tango.reset()
|
||||
bars = []
|
||||
|
||||
ard_params = np.atleast_2d(kernel.input_sensitivity(summarize=False))
|
||||
bottom = 0
|
||||
last_bottom = bottom
|
||||
|
||||
x = np.arange(kernel.input_dim)
|
||||
|
||||
if filtering is None:
|
||||
filtering = kernel.parameter_names(recursive=False)
|
||||
|
||||
for i in range(ard_params.shape[0]):
|
||||
if kernel.parameters[i].name in filtering:
|
||||
c = Tango.nextMedium()
|
||||
bars.append(plot_bars(fig, ax, x, ard_params[i,:], c, kernel.parameters[i].name, bottom=bottom))
|
||||
last_bottom = ard_params[i,:]
|
||||
bottom += last_bottom
|
||||
else:
|
||||
print "filtering out {}".format(kernel.parameters[i].name)
|
||||
|
||||
ax.set_xlim(-.5, kernel.input_dim - .5)
|
||||
add_bar_labels(fig, ax, [bars[-1]], bottom=bottom-last_bottom)
|
||||
|
||||
if legend:
|
||||
if title is '':
|
||||
mode = 'expand'
|
||||
if len(bars) > 1:
|
||||
mode = 'expand'
|
||||
ax.legend(bbox_to_anchor=(0., 1.02, 1., 1.02), loc=3,
|
||||
ncol=len(bars), mode=mode, borderaxespad=0.)
|
||||
fig.tight_layout(rect=(0, 0, 1, .9))
|
||||
else:
|
||||
ax.legend()
|
||||
return ax
|
||||
|
||||
|
||||
|
||||
def plot(kernel,x=None, fignum=None, ax=None, title=None, plot_limits=None, resolution=None, **mpl_kwargs):
|
||||
"""
|
||||
plot a kernel.
|
||||
:param x: the value to use for the other kernel argument (kernels are a function of two variables!)
|
||||
:param fignum: figure number of the plot
|
||||
:param ax: matplotlib axis to plot on
|
||||
:param title: the matplotlib title
|
||||
:param plot_limits: the range over which to plot the kernel
|
||||
:resolution: the resolution of the lines used in plotting
|
||||
:mpl_kwargs avalid keyword arguments to pass through to matplotlib (e.g. lw=7)
|
||||
"""
|
||||
fig, ax = ax_default(fignum,ax)
|
||||
|
||||
if title is None:
|
||||
ax.set_title('%s kernel' % kernel.name)
|
||||
else:
|
||||
ax.set_title(title)
|
||||
|
||||
|
||||
if kernel.input_dim == 1:
|
||||
if x is None:
|
||||
x = np.zeros((1, 1))
|
||||
else:
|
||||
x = np.asarray(x)
|
||||
assert x.size == 1, "The size of the fixed variable x is not 1"
|
||||
x = x.reshape((1, 1))
|
||||
|
||||
if plot_limits == None:
|
||||
xmin, xmax = (x - 5).flatten(), (x + 5).flatten()
|
||||
elif len(plot_limits) == 2:
|
||||
xmin, xmax = plot_limits
|
||||
else:
|
||||
raise ValueError, "Bad limits for plotting"
|
||||
|
||||
Xnew = np.linspace(xmin, xmax, resolution or 201)[:, None]
|
||||
Kx = kernel.K(Xnew, x)
|
||||
ax.plot(Xnew, Kx, **mpl_kwargs)
|
||||
ax.set_xlim(xmin, xmax)
|
||||
ax.set_xlabel("x")
|
||||
ax.set_ylabel("k(x,%0.1f)" % x)
|
||||
|
||||
elif kernel.input_dim == 2:
|
||||
if x is None:
|
||||
x = np.zeros((1, 2))
|
||||
else:
|
||||
x = np.asarray(x)
|
||||
assert x.size == 2, "The size of the fixed variable x is not 2"
|
||||
x = x.reshape((1, 2))
|
||||
|
||||
if plot_limits is None:
|
||||
xmin, xmax = (x - 5).flatten(), (x + 5).flatten()
|
||||
elif len(plot_limits) == 2:
|
||||
xmin, xmax = plot_limits
|
||||
else:
|
||||
raise ValueError, "Bad limits for plotting"
|
||||
|
||||
resolution = resolution or 51
|
||||
xx, yy = np.mgrid[xmin[0]:xmax[0]:1j * resolution, xmin[1]:xmax[1]:1j * resolution]
|
||||
Xnew = np.vstack((xx.flatten(), yy.flatten())).T
|
||||
Kx = kernel.K(Xnew, x)
|
||||
Kx = Kx.reshape(resolution, resolution).T
|
||||
ax.contour(xx, yy, Kx, vmin=Kx.min(), vmax=Kx.max(), cmap=pb.cm.jet, **mpl_kwargs) # @UndefinedVariable
|
||||
ax.set_xlim(xmin[0], xmax[0])
|
||||
ax.set_ylim(xmin[1], xmax[1])
|
||||
ax.set_xlabel("x1")
|
||||
ax.set_ylabel("x2")
|
||||
ax.set_title("k(x1,x2 ; %0.1f,%0.1f)" % (x[0, 0], x[0, 1]))
|
||||
else:
|
||||
raise NotImplementedError, "Cannot plot a kernel with more than two input dimensions"
|
||||
|
|
@ -0,0 +1 @@
|
|||
import controllers
|
||||
|
|
@ -0,0 +1 @@
|
|||
import axis_event_controller, imshow_controller
|
||||
|
|
@ -0,0 +1,147 @@
|
|||
'''
|
||||
Created on 24 Jul 2013
|
||||
|
||||
@author: maxz
|
||||
'''
|
||||
import numpy
|
||||
|
||||
class AxisEventController(object):
|
||||
def __init__(self, ax):
|
||||
self.ax = ax
|
||||
self.activate()
|
||||
def deactivate(self):
|
||||
for cb_class in self.ax.callbacks.callbacks.values():
|
||||
for cb_num in cb_class.keys():
|
||||
self.ax.callbacks.disconnect(cb_num)
|
||||
def activate(self):
|
||||
self.ax.callbacks.connect('xlim_changed', self.xlim_changed)
|
||||
self.ax.callbacks.connect('ylim_changed', self.ylim_changed)
|
||||
def xlim_changed(self, ax):
|
||||
pass
|
||||
def ylim_changed(self, ax):
|
||||
pass
|
||||
|
||||
|
||||
class AxisChangedController(AxisEventController):
|
||||
'''
|
||||
Buffered control of axis limit changes
|
||||
'''
|
||||
_changing = False
|
||||
|
||||
def __init__(self, ax, update_lim=None):
|
||||
'''
|
||||
Constructor
|
||||
'''
|
||||
super(AxisChangedController, self).__init__(ax)
|
||||
self._lim_ratio_threshold = update_lim or .95
|
||||
self._x_lim = self.ax.get_xlim()
|
||||
self._y_lim = self.ax.get_ylim()
|
||||
|
||||
def update(self, ax):
|
||||
pass
|
||||
|
||||
def xlim_changed(self, ax):
|
||||
super(AxisChangedController, self).xlim_changed(ax)
|
||||
if not self._changing and self.lim_changed(ax.get_xlim(), self._x_lim):
|
||||
self._changing = True
|
||||
self._x_lim = ax.get_xlim()
|
||||
self.update(ax)
|
||||
self._changing = False
|
||||
|
||||
def ylim_changed(self, ax):
|
||||
super(AxisChangedController, self).ylim_changed(ax)
|
||||
if not self._changing and self.lim_changed(ax.get_ylim(), self._y_lim):
|
||||
self._changing = True
|
||||
self._y_lim = ax.get_ylim()
|
||||
self.update(ax)
|
||||
self._changing = False
|
||||
|
||||
def extent(self, lim):
|
||||
return numpy.subtract(*lim)
|
||||
|
||||
def lim_changed(self, axlim, savedlim):
|
||||
axextent = self.extent(axlim)
|
||||
extent = self.extent(savedlim)
|
||||
lim_changed = ((axextent / extent) < self._lim_ratio_threshold ** 2
|
||||
or (extent / axextent) < self._lim_ratio_threshold ** 2
|
||||
or ((1 - (self.extent((axlim[0], savedlim[0])) / self.extent((savedlim[0], axlim[1]))))
|
||||
< self._lim_ratio_threshold)
|
||||
or ((1 - (self.extent((savedlim[0], axlim[0])) / self.extent((axlim[0], savedlim[1]))))
|
||||
< self._lim_ratio_threshold)
|
||||
)
|
||||
return lim_changed
|
||||
|
||||
def _buffer_lim(self, lim):
|
||||
# buffer_size = 1 - self._lim_ratio_threshold
|
||||
# extent = self.extent(lim)
|
||||
return lim
|
||||
|
||||
|
||||
class BufferedAxisChangedController(AxisChangedController):
|
||||
def __init__(self, ax, plot_function, plot_limits, resolution=50, update_lim=None, **kwargs):
|
||||
"""
|
||||
Buffered axis changed controller. Controls the buffer and handles update events for when the axes changed.
|
||||
|
||||
Updated plotting will be after first reload (first time will be within plot limits, after that the limits will be buffered)
|
||||
|
||||
:param plot_function:
|
||||
function to use for creating image for plotting (return ndarray-like)
|
||||
plot_function gets called with (2D!) Xtest grid if replotting required
|
||||
:type plot_function: function
|
||||
:param plot_limits:
|
||||
beginning plot limits [xmin, ymin, xmax, ymax]
|
||||
|
||||
:param kwargs: additional kwargs are for pyplot.imshow(**kwargs)
|
||||
"""
|
||||
super(BufferedAxisChangedController, self).__init__(ax, update_lim=update_lim)
|
||||
self.plot_function = plot_function
|
||||
xmin, ymin, xmax, ymax = plot_limits#self._x_lim # self._compute_buffered(*self._x_lim)
|
||||
# imshow acts on the limits of the plot, this is why we need to override the limits here, to make sure the right plot limits are used:
|
||||
self._x_lim = xmin, xmax
|
||||
self._y_lim = ymin, ymax
|
||||
self.resolution = resolution
|
||||
self._not_init = False
|
||||
self.view = self._init_view(self.ax, self.recompute_X(buffered=False), xmin, xmax, ymin, ymax, **kwargs)
|
||||
self._not_init = True
|
||||
|
||||
def update(self, ax):
|
||||
super(BufferedAxisChangedController, self).update(ax)
|
||||
if self._not_init:
|
||||
xmin, xmax = self._compute_buffered(*self._x_lim)
|
||||
ymin, ymax = self._compute_buffered(*self._y_lim)
|
||||
self.update_view(self.view, self.recompute_X(), xmin, xmax, ymin, ymax)
|
||||
|
||||
def _init_view(self, ax, X, xmin, xmax, ymin, ymax):
|
||||
raise NotImplementedError('return view for this controller')
|
||||
|
||||
def update_view(self, view, X, xmin, xmax, ymin, ymax):
|
||||
raise NotImplementedError('update view given in here')
|
||||
|
||||
def get_grid(self, buffered=True):
|
||||
if buffered: comp = self._compute_buffered
|
||||
else: comp = lambda a,b: (a,b)
|
||||
xmin, xmax = comp(*self._x_lim)
|
||||
ymin, ymax = comp(*self._y_lim)
|
||||
x, y = numpy.mgrid[xmin:xmax:1j * self.resolution, ymin:ymax:1j * self.resolution]
|
||||
return numpy.hstack((x.flatten()[:, None], y.flatten()[:, None]))
|
||||
|
||||
def recompute_X(self, buffered=True):
|
||||
X = self.plot_function(self.get_grid(buffered))
|
||||
if isinstance(X, (tuple, list)):
|
||||
for x in X:
|
||||
x.shape = [self.resolution, self.resolution]
|
||||
x[:, :] = x.T[::-1, :]
|
||||
return X
|
||||
return X.reshape(self.resolution, self.resolution).T[::-1, :]
|
||||
|
||||
def _compute_buffered(self, mi, ma):
|
||||
buffersize = self._buffersize()
|
||||
size = ma - mi
|
||||
return mi - (buffersize * size), ma + (buffersize * size)
|
||||
|
||||
def _buffersize(self):
|
||||
try:
|
||||
buffersize = 1. - self._lim_ratio_threshold
|
||||
except:
|
||||
buffersize = .4
|
||||
return buffersize
|
||||
|
|
@ -0,0 +1,71 @@
|
|||
'''
|
||||
Created on 24 Jul 2013
|
||||
|
||||
@author: maxz
|
||||
'''
|
||||
from axis_event_controller import BufferedAxisChangedController
|
||||
import itertools
|
||||
import numpy
|
||||
|
||||
|
||||
class ImshowController(BufferedAxisChangedController):
|
||||
def __init__(self, ax, plot_function, plot_limits, resolution=50, update_lim=.8, **kwargs):
|
||||
"""
|
||||
:param plot_function:
|
||||
function to use for creating image for plotting (return ndarray-like)
|
||||
plot_function gets called with (2D!) Xtest grid if replotting required
|
||||
:type plot_function: function
|
||||
:param plot_limits:
|
||||
beginning plot limits [xmin, ymin, xmax, ymax]
|
||||
|
||||
:param kwargs: additional kwargs are for pyplot.imshow(**kwargs)
|
||||
"""
|
||||
super(ImshowController, self).__init__(ax, plot_function, plot_limits, resolution, update_lim, **kwargs)
|
||||
|
||||
def _init_view(self, ax, X, xmin, xmax, ymin, ymax, **kwargs):
|
||||
return ax.imshow(X, extent=(xmin, xmax,
|
||||
ymin, ymax),
|
||||
vmin=X.min(),
|
||||
vmax=X.max(),
|
||||
**kwargs)
|
||||
|
||||
def update_view(self, view, X, xmin, xmax, ymin, ymax):
|
||||
view.set_data(X)
|
||||
view.set_extent((xmin, xmax, ymin, ymax))
|
||||
|
||||
class ImAnnotateController(ImshowController):
|
||||
def __init__(self, ax, plot_function, plot_limits, resolution=20, update_lim=.99, **kwargs):
|
||||
"""
|
||||
:param plot_function:
|
||||
function to use for creating image for plotting (return ndarray-like)
|
||||
plot_function gets called with (2D!) Xtest grid if replotting required
|
||||
:type plot_function: function
|
||||
:param plot_limits:
|
||||
beginning plot limits [xmin, ymin, xmax, ymax]
|
||||
:param text_props: kwargs for pyplot.text(**text_props)
|
||||
:param kwargs: additional kwargs are for pyplot.imshow(**kwargs)
|
||||
"""
|
||||
super(ImAnnotateController, self).__init__(ax, plot_function, plot_limits, resolution, update_lim, **kwargs)
|
||||
|
||||
def _init_view(self, ax, X, xmin, xmax, ymin, ymax, text_props={}, **kwargs):
|
||||
view = [super(ImAnnotateController, self)._init_view(ax, X[0], xmin, xmax, ymin, ymax, **kwargs)]
|
||||
xoffset, yoffset = self._offsets(xmin, xmax, ymin, ymax)
|
||||
xlin = numpy.linspace(xmin, xmax, self.resolution, endpoint=False)
|
||||
ylin = numpy.linspace(ymin, ymax, self.resolution, endpoint=False)
|
||||
for [i, x], [j, y] in itertools.product(enumerate(xlin), enumerate(ylin[::-1])):
|
||||
view.append(ax.text(x + xoffset, y + yoffset, "{}".format(X[1][j, i]), ha='center', va='center', **text_props))
|
||||
return view
|
||||
|
||||
def update_view(self, view, X, xmin, xmax, ymin, ymax):
|
||||
super(ImAnnotateController, self).update_view(view[0], X[0], xmin, xmax, ymin, ymax)
|
||||
xoffset, yoffset = self._offsets(xmin, xmax, ymin, ymax)
|
||||
xlin = numpy.linspace(xmin, xmax, self.resolution, endpoint=False)
|
||||
ylin = numpy.linspace(ymin, ymax, self.resolution, endpoint=False)
|
||||
for [[i, x], [j, y]], text in itertools.izip(itertools.product(enumerate(xlin), enumerate(ylin[::-1])), view[1:]):
|
||||
text.set_x(x + xoffset)
|
||||
text.set_y(y + yoffset)
|
||||
text.set_text("{}".format(X[1][j, i]))
|
||||
return view
|
||||
|
||||
def _offsets(self, xmin, xmax, ymin, ymax):
|
||||
return (xmax - xmin) / (2 * self.resolution), (ymax - ymin) / (2 * self.resolution)
|
||||
84
GPy/plotting/matplot_dep/mapping_plots.py
Normal file
84
GPy/plotting/matplot_dep/mapping_plots.py
Normal file
|
|
@ -0,0 +1,84 @@
|
|||
# Copyright (c) 2012, GPy authors (see AUTHORS.txt).
|
||||
# Licensed under the BSD 3-clause license (see LICENSE.txt)
|
||||
|
||||
import numpy as np
|
||||
try:
|
||||
import Tango
|
||||
import pylab as pb
|
||||
except:
|
||||
pass
|
||||
from base_plots import x_frame1D, x_frame2D
|
||||
|
||||
|
||||
def plot_mapping(self, plot_limits=None, which_data='all', which_parts='all', resolution=None, levels=20, samples=0, fignum=None, ax=None, fixed_inputs=[], linecol=Tango.colorsHex['darkBlue']):
|
||||
"""
|
||||
Plots the mapping associated with the model.
|
||||
- In one dimension, the function is plotted.
|
||||
- In two dimsensions, a contour-plot shows the function
|
||||
- In higher dimensions, we've not implemented this yet !TODO!
|
||||
|
||||
Can plot only part of the data and part of the posterior functions
|
||||
using which_data and which_functions
|
||||
|
||||
:param plot_limits: The limits of the plot. If 1D [xmin,xmax], if 2D [[xmin,ymin],[xmax,ymax]]. Defaluts to data limits
|
||||
:type plot_limits: np.array
|
||||
:param which_data: which if the training data to plot (default all)
|
||||
:type which_data: 'all' or a slice object to slice self.X, self.Y
|
||||
:param which_parts: which of the kernel functions to plot (additively)
|
||||
:type which_parts: 'all', or list of bools
|
||||
:param resolution: the number of intervals to sample the GP on. Defaults to 200 in 1D and 50 (a 50x50 grid) in 2D
|
||||
:type resolution: int
|
||||
:param levels: number of levels to plot in a contour plot.
|
||||
:type levels: int
|
||||
:param samples: the number of a posteriori samples to plot
|
||||
:type samples: int
|
||||
:param fignum: figure to plot on.
|
||||
:type fignum: figure number
|
||||
:param ax: axes to plot on.
|
||||
:type ax: axes handle
|
||||
:param fixed_inputs: a list of tuple [(i,v), (i,v)...], specifying that input index i should be set to value v.
|
||||
:type fixed_inputs: a list of tuples
|
||||
:param linecol: color of line to plot.
|
||||
:type linecol:
|
||||
:param levels: for 2D plotting, the number of contour levels to use is ax is None, create a new figure
|
||||
|
||||
"""
|
||||
# TODO include samples
|
||||
if which_data == 'all':
|
||||
which_data = slice(None)
|
||||
|
||||
if ax is None:
|
||||
fig = pb.figure(num=fignum)
|
||||
ax = fig.add_subplot(111)
|
||||
|
||||
plotdims = self.input_dim - len(fixed_inputs)
|
||||
|
||||
if plotdims == 1:
|
||||
|
||||
Xu = self.X * self._Xscale + self._Xoffset # NOTE self.X are the normalized values now
|
||||
|
||||
fixed_dims = np.array([i for i,v in fixed_inputs])
|
||||
freedim = np.setdiff1d(np.arange(self.input_dim),fixed_dims)
|
||||
|
||||
Xnew, xmin, xmax = x_frame1D(Xu[:,freedim], plot_limits=plot_limits)
|
||||
Xgrid = np.empty((Xnew.shape[0],self.input_dim))
|
||||
Xgrid[:,freedim] = Xnew
|
||||
for i,v in fixed_inputs:
|
||||
Xgrid[:,i] = v
|
||||
|
||||
f = self.predict(Xgrid, which_parts=which_parts)
|
||||
for d in range(y.shape[1]):
|
||||
ax.plot(Xnew, f[:, d], edgecol=linecol)
|
||||
|
||||
elif self.X.shape[1] == 2:
|
||||
resolution = resolution or 50
|
||||
Xnew, _, _, xmin, xmax = x_frame2D(self.X, plot_limits, resolution)
|
||||
x, y = np.linspace(xmin[0], xmax[0], resolution), np.linspace(xmin[1], xmax[1], resolution)
|
||||
f = self.predict(Xnew, which_parts=which_parts)
|
||||
m = m.reshape(resolution, resolution).T
|
||||
ax.contour(x, y, f, levels, vmin=m.min(), vmax=m.max(), cmap=pb.cm.jet) # @UndefinedVariable
|
||||
ax.set_xlim(xmin[0], xmax[0])
|
||||
ax.set_ylim(xmin[1], xmax[1])
|
||||
|
||||
else:
|
||||
raise NotImplementedError, "Cannot define a frame with more than two input dimensions"
|
||||
175
GPy/plotting/matplot_dep/maps.py
Normal file
175
GPy/plotting/matplot_dep/maps.py
Normal file
|
|
@ -0,0 +1,175 @@
|
|||
# Copyright (c) 2012, GPy authors (see AUTHORS.txt).
|
||||
# Licensed under the BSD 3-clause license (see LICENSE.txt)
|
||||
import numpy as np
|
||||
try:
|
||||
import pylab as pb
|
||||
from matplotlib.patches import Polygon
|
||||
from matplotlib.collections import PatchCollection
|
||||
#from matplotlib import cm
|
||||
pb.ion()
|
||||
except:
|
||||
pass
|
||||
import re
|
||||
|
||||
def plot(shape_records,facecolor='w',edgecolor='k',linewidths=.5, ax=None,xlims=None,ylims=None):
|
||||
"""
|
||||
Plot the geometry of a shapefile
|
||||
|
||||
:param shape_records: geometry and attributes list
|
||||
:type shape_records: ShapeRecord object (output of a shapeRecords() method)
|
||||
:param facecolor: color to be used to fill in polygons
|
||||
:param edgecolor: color to be used for lines
|
||||
:param ax: axes to plot on.
|
||||
:type ax: axes handle
|
||||
"""
|
||||
#Axes handle
|
||||
if ax is None:
|
||||
fig = pb.figure()
|
||||
ax = fig.add_subplot(111)
|
||||
|
||||
#Iterate over shape_records
|
||||
for srec in shape_records:
|
||||
points = np.vstack(srec.shape.points)
|
||||
sparts = srec.shape.parts
|
||||
par = list(sparts) + [points.shape[0]]
|
||||
|
||||
polygs = []
|
||||
for pj in xrange(len(sparts)):
|
||||
polygs.append(Polygon(points[par[pj]:par[pj+1]]))
|
||||
ax.add_collection(PatchCollection(polygs,facecolor=facecolor,edgecolor=edgecolor, linewidths=linewidths))
|
||||
|
||||
#Plot limits
|
||||
_box = np.vstack([srec.shape.bbox for srec in shape_records])
|
||||
minx,miny = np.min(_box[:,:2],0)
|
||||
maxx,maxy = np.max(_box[:,2:],0)
|
||||
|
||||
if xlims is not None:
|
||||
minx,maxx = xlims
|
||||
if ylims is not None:
|
||||
miny,maxy = ylims
|
||||
ax.set_xlim(minx,maxx)
|
||||
ax.set_ylim(miny,maxy)
|
||||
|
||||
|
||||
def string_match(sf,regex,field=2):
|
||||
"""
|
||||
Return the geometry and attributes of a shapefile whose fields match a regular expression given
|
||||
|
||||
:param sf: shapefile
|
||||
:type sf: shapefile object
|
||||
:regex: regular expression to match
|
||||
:type regex: string
|
||||
:field: field number to be matched with the regex
|
||||
:type field: integer
|
||||
"""
|
||||
index = []
|
||||
shape_records = []
|
||||
for rec in enumerate(sf.shapeRecords()):
|
||||
m = re.search(regex,rec[1].record[field])
|
||||
if m is not None:
|
||||
index.append(rec[0])
|
||||
shape_records.append(rec[1])
|
||||
return index,shape_records
|
||||
|
||||
def bbox_match(sf,bbox,inside_only=True):
|
||||
"""
|
||||
Return the geometry and attributes of a shapefile that lie within (or intersect) a bounding box
|
||||
|
||||
:param sf: shapefile
|
||||
:type sf: shapefile object
|
||||
:param bbox: bounding box
|
||||
:type bbox: list of floats [x_min,y_min,x_max,y_max]
|
||||
:inside_only: True if the objects returned are those that lie within the bbox and False if the objects returned are any that intersect the bbox
|
||||
:type inside_only: Boolean
|
||||
"""
|
||||
A,B,C,D = bbox
|
||||
index = []
|
||||
shape_records = []
|
||||
for rec in enumerate(sf.shapeRecords()):
|
||||
a,b,c,d = rec[1].shape.bbox
|
||||
if inside_only:
|
||||
if A <= a and B <= b and C >= c and D >= d:
|
||||
index.append(rec[0])
|
||||
shape_records.append(rec[1])
|
||||
else:
|
||||
cond1 = A <= a and B <= b and C >= a and D >= b
|
||||
cond2 = A <= c and B <= d and C >= c and D >= d
|
||||
cond3 = A <= a and D >= d and C >= a and B <= d
|
||||
cond4 = A <= c and D >= b and C >= c and B <= b
|
||||
cond5 = a <= C and b <= B and d >= D
|
||||
cond6 = c <= A and b <= B and d >= D
|
||||
cond7 = d <= B and a <= A and c >= C
|
||||
cond8 = b <= D and a <= A and c >= C
|
||||
if cond1 or cond2 or cond3 or cond4 or cond5 or cond6 or cond7 or cond8:
|
||||
index.append(rec[0])
|
||||
shape_records.append(rec[1])
|
||||
return index,shape_records
|
||||
|
||||
|
||||
def plot_bbox(sf,bbox,inside_only=True):
|
||||
"""
|
||||
Plot the geometry of a shapefile within a bbox
|
||||
|
||||
:param sf: shapefile
|
||||
:type sf: shapefile object
|
||||
:param bbox: bounding box
|
||||
:type bbox: list of floats [x_min,y_min,x_max,y_max]
|
||||
:inside_only: True if the objects returned are those that lie within the bbox and False if the objects returned are any that intersect the bbox
|
||||
:type inside_only: Boolean
|
||||
"""
|
||||
index,shape_records = bbox_match(sf,bbox,inside_only)
|
||||
A,B,C,D = bbox
|
||||
plot(shape_records,xlims=[bbox[0],bbox[2]],ylims=[bbox[1],bbox[3]])
|
||||
|
||||
def plot_string_match(sf,regex,field,**kwargs):
|
||||
"""
|
||||
Plot the geometry of a shapefile whose fields match a regular expression given
|
||||
|
||||
:param sf: shapefile
|
||||
:type sf: shapefile object
|
||||
:regex: regular expression to match
|
||||
:type regex: string
|
||||
:field: field number to be matched with the regex
|
||||
:type field: integer
|
||||
"""
|
||||
index,shape_records = string_match(sf,regex,field)
|
||||
plot(shape_records,**kwargs)
|
||||
|
||||
|
||||
def new_shape_string(sf,name,regex,field=2,type=None):
|
||||
import shapefile
|
||||
if type is None:
|
||||
type = shapefile.POINT
|
||||
newshp = shapefile.Writer(shapeType = sf.shapeType)
|
||||
newshp.autoBalance = 1
|
||||
|
||||
index,shape_records = string_match(sf,regex,field)
|
||||
|
||||
_fi = [sf.fields[j] for j in index]
|
||||
for f in _fi:
|
||||
newshp.field(name=f[0],fieldType=f[1],size=f[2],decimal=f[3])
|
||||
|
||||
_shre = shape_records
|
||||
for sr in _shre:
|
||||
_points = []
|
||||
_parts = []
|
||||
for point in sr.shape.points:
|
||||
_points.append(point)
|
||||
_parts.append(_points)
|
||||
|
||||
newshp.line(parts=_parts)
|
||||
newshp.records.append(sr.record)
|
||||
print len(sr.record)
|
||||
|
||||
newshp.save(name)
|
||||
print index
|
||||
|
||||
def apply_bbox(sf,ax):
|
||||
"""
|
||||
Use bbox as xlim and ylim in ax
|
||||
"""
|
||||
limits = sf.bbox
|
||||
xlim = limits[0],limits[2]
|
||||
ylim = limits[1],limits[3]
|
||||
ax.set_xlim(xlim)
|
||||
ax.set_ylim(ylim)
|
||||
188
GPy/plotting/matplot_dep/models_plots.py
Normal file
188
GPy/plotting/matplot_dep/models_plots.py
Normal file
|
|
@ -0,0 +1,188 @@
|
|||
# Copyright (c) 2012, GPy authors (see AUTHORS.txt).
|
||||
# Licensed under the BSD 3-clause license (see LICENSE.txt)
|
||||
|
||||
try:
|
||||
import Tango
|
||||
import pylab as pb
|
||||
except:
|
||||
pass
|
||||
import numpy as np
|
||||
from base_plots import gpplot, x_frame1D, x_frame2D
|
||||
from ...models.gp_coregionalized_regression import GPCoregionalizedRegression
|
||||
from ...models.sparse_gp_coregionalized_regression import SparseGPCoregionalizedRegression
|
||||
from scipy import sparse
|
||||
|
||||
def plot_fit(model, plot_limits=None, which_data_rows='all',
|
||||
which_data_ycols='all', fixed_inputs=[],
|
||||
levels=20, samples=0, fignum=None, ax=None, resolution=None,
|
||||
plot_raw=False,
|
||||
linecol=Tango.colorsHex['darkBlue'],fillcol=Tango.colorsHex['lightBlue'], Y_metadata=None, data_symbol='kx'):
|
||||
"""
|
||||
Plot the posterior of the GP.
|
||||
- In one dimension, the function is plotted with a shaded region identifying two standard deviations.
|
||||
- In two dimsensions, a contour-plot shows the mean predicted function
|
||||
- In higher dimensions, use fixed_inputs to plot the GP with some of the inputs fixed.
|
||||
|
||||
Can plot only part of the data and part of the posterior functions
|
||||
using which_data_rowsm which_data_ycols.
|
||||
|
||||
:param plot_limits: The limits of the plot. If 1D [xmin,xmax], if 2D [[xmin,ymin],[xmax,ymax]]. Defaluts to data limits
|
||||
:type plot_limits: np.array
|
||||
:param which_data_rows: which of the training data to plot (default all)
|
||||
:type which_data_rows: 'all' or a slice object to slice model.X, model.Y
|
||||
:param which_data_ycols: when the data has several columns (independant outputs), only plot these
|
||||
:type which_data_rows: 'all' or a list of integers
|
||||
:param fixed_inputs: a list of tuple [(i,v), (i,v)...], specifying that input index i should be set to value v.
|
||||
:type fixed_inputs: a list of tuples
|
||||
:param resolution: the number of intervals to sample the GP on. Defaults to 200 in 1D and 50 (a 50x50 grid) in 2D
|
||||
:type resolution: int
|
||||
:param levels: number of levels to plot in a contour plot.
|
||||
:type levels: int
|
||||
:param samples: the number of a posteriori samples to plot
|
||||
:type samples: int
|
||||
:param fignum: figure to plot on.
|
||||
:type fignum: figure number
|
||||
:param ax: axes to plot on.
|
||||
:type ax: axes handle
|
||||
:type output: integer (first output is 0)
|
||||
:param linecol: color of line to plot.
|
||||
:type linecol:
|
||||
:param fillcol: color of fill
|
||||
:param levels: for 2D plotting, the number of contour levels to use is ax is None, create a new figure
|
||||
"""
|
||||
#deal with optional arguments
|
||||
if which_data_rows == 'all':
|
||||
which_data_rows = slice(None)
|
||||
if which_data_ycols == 'all':
|
||||
which_data_ycols = np.arange(model.output_dim)
|
||||
#if len(which_data_ycols)==0:
|
||||
#raise ValueError('No data selected for plotting')
|
||||
if ax is None:
|
||||
fig = pb.figure(num=fignum)
|
||||
ax = fig.add_subplot(111)
|
||||
|
||||
if hasattr(model, 'has_uncertain_inputs') and model.has_uncertain_inputs():
|
||||
X = model.X.mean
|
||||
X_variance = model.X.variance
|
||||
else:
|
||||
X = model.X
|
||||
Y = model.Y
|
||||
if sparse.issparse(Y): Y = Y.todense().view(np.ndarray)
|
||||
|
||||
if hasattr(model, 'Z'): Z = model.Z
|
||||
|
||||
#work out what the inputs are for plotting (1D or 2D)
|
||||
fixed_dims = np.array([i for i,v in fixed_inputs])
|
||||
free_dims = np.setdiff1d(np.arange(model.input_dim),fixed_dims)
|
||||
plots = {}
|
||||
#one dimensional plotting
|
||||
if len(free_dims) == 1:
|
||||
|
||||
#define the frame on which to plot
|
||||
Xnew, xmin, xmax = x_frame1D(X[:,free_dims], plot_limits=plot_limits, resolution=resolution or 200)
|
||||
Xgrid = np.empty((Xnew.shape[0],model.input_dim))
|
||||
Xgrid[:,free_dims] = Xnew
|
||||
for i,v in fixed_inputs:
|
||||
Xgrid[:,i] = v
|
||||
|
||||
#make a prediction on the frame and plot it
|
||||
if plot_raw:
|
||||
m, v = model._raw_predict(Xgrid)
|
||||
lower = m - 2*np.sqrt(v)
|
||||
upper = m + 2*np.sqrt(v)
|
||||
else:
|
||||
if isinstance(model,GPCoregionalizedRegression) or isinstance(model,SparseGPCoregionalizedRegression):
|
||||
meta = {'output_index': Xgrid[:,-1:].astype(np.int)}
|
||||
else:
|
||||
meta = None
|
||||
m, v = model.predict(Xgrid, full_cov=False, Y_metadata=meta)
|
||||
lower, upper = model.predict_quantiles(Xgrid, Y_metadata=meta)
|
||||
|
||||
|
||||
for d in which_data_ycols:
|
||||
plots['gpplot'] = gpplot(Xnew, m[:, d], lower[:, d], upper[:, d], ax=ax, edgecol=linecol, fillcol=fillcol)
|
||||
if not plot_raw: plots['dataplot'] = ax.plot(X[which_data_rows,free_dims], Y[which_data_rows, d], data_symbol, mew=1.5)
|
||||
|
||||
#optionally plot some samples
|
||||
if samples: #NOTE not tested with fixed_inputs
|
||||
Ysim = model.posterior_samples(Xgrid, samples)
|
||||
for yi in Ysim.T:
|
||||
plots['posterior_samples'] = ax.plot(Xnew, yi[:,None], Tango.colorsHex['darkBlue'], linewidth=0.25)
|
||||
#ax.plot(Xnew, yi[:,None], marker='x', linestyle='--',color=Tango.colorsHex['darkBlue']) #TODO apply this line for discrete outputs.
|
||||
|
||||
|
||||
#add error bars for uncertain (if input uncertainty is being modelled)
|
||||
if hasattr(model,"has_uncertain_inputs") and model.has_uncertain_inputs():
|
||||
plots['xerrorbar'] = ax.errorbar(X[which_data_rows, free_dims].flatten(), Y[which_data_rows, which_data_ycols].flatten(),
|
||||
xerr=2 * np.sqrt(X_variance[which_data_rows, free_dims].flatten()),
|
||||
ecolor='k', fmt=None, elinewidth=.5, alpha=.5)
|
||||
|
||||
|
||||
#set the limits of the plot to some sensible values
|
||||
ymin, ymax = min(np.append(Y[which_data_rows, which_data_ycols].flatten(), lower)), max(np.append(Y[which_data_rows, which_data_ycols].flatten(), upper))
|
||||
ymin, ymax = ymin - 0.1 * (ymax - ymin), ymax + 0.1 * (ymax - ymin)
|
||||
ax.set_xlim(xmin, xmax)
|
||||
ax.set_ylim(ymin, ymax)
|
||||
|
||||
#add inducing inputs (if a sparse model is used)
|
||||
if hasattr(model,"Z"):
|
||||
#Zu = model.Z[:,free_dims] * model._Xscale[:,free_dims] + model._Xoffset[:,free_dims]
|
||||
if isinstance(model,SparseGPCoregionalizedRegression):
|
||||
Z = Z[Z[:,-1] == Y_metadata['output_index'],:]
|
||||
Zu = Z[:,free_dims]
|
||||
z_height = ax.get_ylim()[0]
|
||||
plots['inducing_inputs'] = ax.plot(Zu, np.zeros_like(Zu) + z_height, 'r|', mew=1.5, markersize=12)
|
||||
|
||||
|
||||
|
||||
#2D plotting
|
||||
elif len(free_dims) == 2:
|
||||
|
||||
#define the frame for plotting on
|
||||
resolution = resolution or 50
|
||||
Xnew, _, _, xmin, xmax = x_frame2D(X[:,free_dims], plot_limits, resolution)
|
||||
Xgrid = np.empty((Xnew.shape[0],model.input_dim))
|
||||
Xgrid[:,free_dims] = Xnew
|
||||
for i,v in fixed_inputs:
|
||||
Xgrid[:,i] = v
|
||||
x, y = np.linspace(xmin[0], xmax[0], resolution), np.linspace(xmin[1], xmax[1], resolution)
|
||||
|
||||
#predict on the frame and plot
|
||||
if plot_raw:
|
||||
m, _ = model._raw_predict(Xgrid)
|
||||
else:
|
||||
if isinstance(model,GPCoregionalizedRegression) or isinstance(model,SparseGPCoregionalizedRegression):
|
||||
meta = {'output_index': Xgrid[:,-1:].astype(np.int)}
|
||||
else:
|
||||
meta = None
|
||||
m, v = model.predict(Xgrid, full_cov=False, Y_metadata=meta)
|
||||
for d in which_data_ycols:
|
||||
m_d = m[:,d].reshape(resolution, resolution).T
|
||||
plots['contour'] = ax.contour(x, y, m_d, levels, vmin=m.min(), vmax=m.max(), cmap=pb.cm.jet)
|
||||
if not plot_raw: plots['dataplot'] = ax.scatter(X[which_data_rows, free_dims[0]], X[which_data_rows, free_dims[1]], 40, Y[which_data_rows, d], cmap=pb.cm.jet, vmin=m.min(), vmax=m.max(), linewidth=0.)
|
||||
|
||||
#set the limits of the plot to some sensible values
|
||||
ax.set_xlim(xmin[0], xmax[0])
|
||||
ax.set_ylim(xmin[1], xmax[1])
|
||||
|
||||
if samples:
|
||||
warnings.warn("Samples are rather difficult to plot for 2D inputs...")
|
||||
|
||||
#add inducing inputs (if a sparse model is used)
|
||||
if hasattr(model,"Z"):
|
||||
#Zu = model.Z[:,free_dims] * model._Xscale[:,free_dims] + model._Xoffset[:,free_dims]
|
||||
Zu = Z[:,free_dims]
|
||||
plots['inducing_inputs'] = ax.plot(Zu[:,free_dims[0]], Zu[:,free_dims[1]], 'wo')
|
||||
|
||||
else:
|
||||
raise NotImplementedError, "Cannot define a frame with more than two input dimensions"
|
||||
return plots
|
||||
|
||||
def plot_fit_f(model, *args, **kwargs):
|
||||
"""
|
||||
Plot the GP's view of the world, where the data is normalized and before applying a likelihood.
|
||||
|
||||
All args and kwargs are passed on to models_plots.plot.
|
||||
"""
|
||||
kwargs['plot_raw'] = True
|
||||
plot_fit(model,*args, **kwargs)
|
||||
331
GPy/plotting/matplot_dep/netpbmfile.py
Normal file
331
GPy/plotting/matplot_dep/netpbmfile.py
Normal file
|
|
@ -0,0 +1,331 @@
|
|||
#!/usr/bin/env python
|
||||
# -*- coding: utf-8 -*-
|
||||
# netpbmfile.py
|
||||
|
||||
# Copyright (c) 2011-2013, Christoph Gohlke
|
||||
# Copyright (c) 2011-2013, The Regents of the University of California
|
||||
# Produced at the Laboratory for Fluorescence Dynamics.
|
||||
# All rights reserved.
|
||||
#
|
||||
# Redistribution and use in source and binary forms, with or without
|
||||
# modification, are permitted provided that the following conditions are met:
|
||||
#
|
||||
# * Redistributions of source code must retain the above copyright
|
||||
# notice, this list of conditions and the following disclaimer.
|
||||
# * Redistributions in binary form must reproduce the above copyright
|
||||
# notice, this list of conditions and the following disclaimer in the
|
||||
# documentation and/or other materials provided with the distribution.
|
||||
# * Neither the name of the copyright holders nor the names of any
|
||||
# contributors may be used to endorse or promote products derived
|
||||
# from this software without specific prior written permission.
|
||||
#
|
||||
# THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
|
||||
# AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
# IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
|
||||
# ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
|
||||
# LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
|
||||
# CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
|
||||
# SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
|
||||
# INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
|
||||
# CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
|
||||
# ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
|
||||
# POSSIBILITY OF SUCH DAMAGE.
|
||||
|
||||
"""Read and write image data from respectively to Netpbm files.
|
||||
|
||||
This implementation follows the Netpbm format specifications at
|
||||
http://netpbm.sourceforge.net/doc/. No gamma correction is performed.
|
||||
|
||||
The following image formats are supported: PBM (bi-level), PGM (grayscale),
|
||||
PPM (color), PAM (arbitrary), XV thumbnail (RGB332, read-only).
|
||||
|
||||
:Author:
|
||||
`Christoph Gohlke <http://www.lfd.uci.edu/~gohlke/>`_
|
||||
|
||||
:Organization:
|
||||
Laboratory for Fluorescence Dynamics, University of California, Irvine
|
||||
|
||||
:Version: 2013.01.18
|
||||
|
||||
Requirements
|
||||
------------
|
||||
* `CPython 2.7, 3.2 or 3.3 <http://www.python.org>`_
|
||||
* `Numpy 1.7 <http://www.numpy.org>`_
|
||||
* `Matplotlib 1.2 <http://www.matplotlib.org>`_ (optional for plotting)
|
||||
|
||||
Examples
|
||||
--------
|
||||
>>> im1 = numpy.array([[0, 1],[65534, 65535]], dtype=numpy.uint16)
|
||||
>>> imsave('_tmp.pgm', im1)
|
||||
>>> im2 = imread('_tmp.pgm')
|
||||
>>> assert numpy.all(im1 == im2)
|
||||
|
||||
"""
|
||||
|
||||
from __future__ import division, print_function
|
||||
|
||||
import sys
|
||||
import re
|
||||
import math
|
||||
from copy import deepcopy
|
||||
|
||||
import numpy
|
||||
|
||||
__version__ = '2013.01.18'
|
||||
__docformat__ = 'restructuredtext en'
|
||||
__all__ = ['imread', 'imsave', 'NetpbmFile']
|
||||
|
||||
|
||||
def imread(filename, *args, **kwargs):
|
||||
"""Return image data from Netpbm file as numpy array.
|
||||
|
||||
`args` and `kwargs` are arguments to NetpbmFile.asarray().
|
||||
|
||||
Examples
|
||||
--------
|
||||
>>> image = imread('_tmp.pgm')
|
||||
|
||||
"""
|
||||
try:
|
||||
netpbm = NetpbmFile(filename)
|
||||
image = netpbm.asarray()
|
||||
finally:
|
||||
netpbm.close()
|
||||
return image
|
||||
|
||||
|
||||
def imsave(filename, data, maxval=None, pam=False):
|
||||
"""Write image data to Netpbm file.
|
||||
|
||||
Examples
|
||||
--------
|
||||
>>> image = numpy.array([[0, 1],[65534, 65535]], dtype=numpy.uint16)
|
||||
>>> imsave('_tmp.pgm', image)
|
||||
|
||||
"""
|
||||
try:
|
||||
netpbm = NetpbmFile(data, maxval=maxval)
|
||||
netpbm.write(filename, pam=pam)
|
||||
finally:
|
||||
netpbm.close()
|
||||
|
||||
|
||||
class NetpbmFile(object):
|
||||
"""Read and write Netpbm PAM, PBM, PGM, PPM, files."""
|
||||
|
||||
_types = {b'P1': b'BLACKANDWHITE', b'P2': b'GRAYSCALE', b'P3': b'RGB',
|
||||
b'P4': b'BLACKANDWHITE', b'P5': b'GRAYSCALE', b'P6': b'RGB',
|
||||
b'P7 332': b'RGB', b'P7': b'RGB_ALPHA'}
|
||||
|
||||
def __init__(self, arg=None, **kwargs):
|
||||
"""Initialize instance from filename, open file, or numpy array."""
|
||||
for attr in ('header', 'magicnum', 'width', 'height', 'maxval',
|
||||
'depth', 'tupltypes', '_filename', '_fh', '_data'):
|
||||
setattr(self, attr, None)
|
||||
if arg is None:
|
||||
self._fromdata([], **kwargs)
|
||||
elif isinstance(arg, basestring):
|
||||
self._fh = open(arg, 'rb')
|
||||
self._filename = arg
|
||||
self._fromfile(self._fh, **kwargs)
|
||||
elif hasattr(arg, 'seek'):
|
||||
self._fromfile(arg, **kwargs)
|
||||
self._fh = arg
|
||||
else:
|
||||
self._fromdata(arg, **kwargs)
|
||||
|
||||
def asarray(self, copy=True, cache=False, **kwargs):
|
||||
"""Return image data from file as numpy array."""
|
||||
data = self._data
|
||||
if data is None:
|
||||
data = self._read_data(self._fh, **kwargs)
|
||||
if cache:
|
||||
self._data = data
|
||||
else:
|
||||
return data
|
||||
return deepcopy(data) if copy else data
|
||||
|
||||
def write(self, arg, **kwargs):
|
||||
"""Write instance to file."""
|
||||
if hasattr(arg, 'seek'):
|
||||
self._tofile(arg, **kwargs)
|
||||
else:
|
||||
with open(arg, 'wb') as fid:
|
||||
self._tofile(fid, **kwargs)
|
||||
|
||||
def close(self):
|
||||
"""Close open file. Future asarray calls might fail."""
|
||||
if self._filename and self._fh:
|
||||
self._fh.close()
|
||||
self._fh = None
|
||||
|
||||
def __del__(self):
|
||||
self.close()
|
||||
|
||||
def _fromfile(self, fh):
|
||||
"""Initialize instance from open file."""
|
||||
fh.seek(0)
|
||||
data = fh.read(4096)
|
||||
if (len(data) < 7) or not (b'0' < data[1:2] < b'8'):
|
||||
raise ValueError("Not a Netpbm file:\n%s" % data[:32])
|
||||
try:
|
||||
self._read_pam_header(data)
|
||||
except Exception:
|
||||
try:
|
||||
self._read_pnm_header(data)
|
||||
except Exception:
|
||||
raise ValueError("Not a Netpbm file:\n%s" % data[:32])
|
||||
|
||||
def _read_pam_header(self, data):
|
||||
"""Read PAM header and initialize instance."""
|
||||
regroups = re.search(
|
||||
b"(^P7[\n\r]+(?:(?:[\n\r]+)|(?:#.*)|"
|
||||
b"(HEIGHT\s+\d+)|(WIDTH\s+\d+)|(DEPTH\s+\d+)|(MAXVAL\s+\d+)|"
|
||||
b"(?:TUPLTYPE\s+\w+))*ENDHDR\n)", data).groups()
|
||||
self.header = regroups[0]
|
||||
self.magicnum = b'P7'
|
||||
for group in regroups[1:]:
|
||||
key, value = group.split()
|
||||
setattr(self, unicode(key).lower(), int(value))
|
||||
matches = re.findall(b"(TUPLTYPE\s+\w+)", self.header)
|
||||
self.tupltypes = [s.split(None, 1)[1] for s in matches]
|
||||
|
||||
def _read_pnm_header(self, data):
|
||||
"""Read PNM header and initialize instance."""
|
||||
bpm = data[1:2] in b"14"
|
||||
regroups = re.search(b"".join((
|
||||
b"(^(P[123456]|P7 332)\s+(?:#.*[\r\n])*",
|
||||
b"\s*(\d+)\s+(?:#.*[\r\n])*",
|
||||
b"\s*(\d+)\s+(?:#.*[\r\n])*" * (not bpm),
|
||||
b"\s*(\d+)\s(?:\s*#.*[\r\n]\s)*)")), data).groups() + (1, ) * bpm
|
||||
self.header = regroups[0]
|
||||
self.magicnum = regroups[1]
|
||||
self.width = int(regroups[2])
|
||||
self.height = int(regroups[3])
|
||||
self.maxval = int(regroups[4])
|
||||
self.depth = 3 if self.magicnum in b"P3P6P7 332" else 1
|
||||
self.tupltypes = [self._types[self.magicnum]]
|
||||
|
||||
def _read_data(self, fh, byteorder='>'):
|
||||
"""Return image data from open file as numpy array."""
|
||||
fh.seek(len(self.header))
|
||||
data = fh.read()
|
||||
dtype = 'u1' if self.maxval < 256 else byteorder + 'u2'
|
||||
depth = 1 if self.magicnum == b"P7 332" else self.depth
|
||||
shape = [-1, self.height, self.width, depth]
|
||||
size = numpy.prod(shape[1:])
|
||||
if self.magicnum in b"P1P2P3":
|
||||
data = numpy.array(data.split(None, size)[:size], dtype)
|
||||
data = data.reshape(shape)
|
||||
elif self.maxval == 1:
|
||||
shape[2] = int(math.ceil(self.width / 8))
|
||||
data = numpy.frombuffer(data, dtype).reshape(shape)
|
||||
data = numpy.unpackbits(data, axis=-2)[:, :, :self.width, :]
|
||||
else:
|
||||
data = numpy.frombuffer(data, dtype)
|
||||
data = data[:size * (data.size // size)].reshape(shape)
|
||||
if data.shape[0] < 2:
|
||||
data = data.reshape(data.shape[1:])
|
||||
if data.shape[-1] < 2:
|
||||
data = data.reshape(data.shape[:-1])
|
||||
if self.magicnum == b"P7 332":
|
||||
rgb332 = numpy.array(list(numpy.ndindex(8, 8, 4)), numpy.uint8)
|
||||
rgb332 *= [36, 36, 85]
|
||||
data = numpy.take(rgb332, data, axis=0)
|
||||
return data
|
||||
|
||||
def _fromdata(self, data, maxval=None):
|
||||
"""Initialize instance from numpy array."""
|
||||
data = numpy.array(data, ndmin=2, copy=True)
|
||||
if data.dtype.kind not in "uib":
|
||||
raise ValueError("not an integer type: %s" % data.dtype)
|
||||
if data.dtype.kind == 'i' and numpy.min(data) < 0:
|
||||
raise ValueError("data out of range: %i" % numpy.min(data))
|
||||
if maxval is None:
|
||||
maxval = numpy.max(data)
|
||||
maxval = 255 if maxval < 256 else 65535
|
||||
if maxval < 0 or maxval > 65535:
|
||||
raise ValueError("data out of range: %i" % maxval)
|
||||
data = data.astype('u1' if maxval < 256 else '>u2')
|
||||
self._data = data
|
||||
if data.ndim > 2 and data.shape[-1] in (3, 4):
|
||||
self.depth = data.shape[-1]
|
||||
self.width = data.shape[-2]
|
||||
self.height = data.shape[-3]
|
||||
self.magicnum = b'P7' if self.depth == 4 else b'P6'
|
||||
else:
|
||||
self.depth = 1
|
||||
self.width = data.shape[-1]
|
||||
self.height = data.shape[-2]
|
||||
self.magicnum = b'P5' if maxval > 1 else b'P4'
|
||||
self.maxval = maxval
|
||||
self.tupltypes = [self._types[self.magicnum]]
|
||||
self.header = self._header()
|
||||
|
||||
def _tofile(self, fh, pam=False):
|
||||
"""Write Netbm file."""
|
||||
fh.seek(0)
|
||||
fh.write(self._header(pam))
|
||||
data = self.asarray(copy=False)
|
||||
if self.maxval == 1:
|
||||
data = numpy.packbits(data, axis=-1)
|
||||
data.tofile(fh)
|
||||
|
||||
def _header(self, pam=False):
|
||||
"""Return file header as byte string."""
|
||||
if pam or self.magicnum == b'P7':
|
||||
header = "\n".join((
|
||||
"P7",
|
||||
"HEIGHT %i" % self.height,
|
||||
"WIDTH %i" % self.width,
|
||||
"DEPTH %i" % self.depth,
|
||||
"MAXVAL %i" % self.maxval,
|
||||
"\n".join("TUPLTYPE %s" % unicode(i) for i in self.tupltypes),
|
||||
"ENDHDR\n"))
|
||||
elif self.maxval == 1:
|
||||
header = "P4 %i %i\n" % (self.width, self.height)
|
||||
elif self.depth == 1:
|
||||
header = "P5 %i %i %i\n" % (self.width, self.height, self.maxval)
|
||||
else:
|
||||
header = "P6 %i %i %i\n" % (self.width, self.height, self.maxval)
|
||||
if sys.version_info[0] > 2:
|
||||
header = bytes(header, 'ascii')
|
||||
return header
|
||||
|
||||
def __str__(self):
|
||||
"""Return information about instance."""
|
||||
return unicode(self.header)
|
||||
|
||||
|
||||
if sys.version_info[0] > 2:
|
||||
basestring = str
|
||||
unicode = lambda x: str(x, 'ascii')
|
||||
|
||||
if __name__ == "__main__":
|
||||
# Show images specified on command line or all images in current directory
|
||||
from glob import glob
|
||||
from matplotlib import pyplot
|
||||
files = sys.argv[1:] if len(sys.argv) > 1 else glob('*.p*m')
|
||||
for fname in files:
|
||||
try:
|
||||
pam = NetpbmFile(fname)
|
||||
img = pam.asarray(copy=False)
|
||||
if False:
|
||||
pam.write('_tmp.pgm.out', pam=True)
|
||||
img2 = imread('_tmp.pgm.out')
|
||||
assert numpy.all(img == img2)
|
||||
imsave('_tmp.pgm.out', img)
|
||||
img2 = imread('_tmp.pgm.out')
|
||||
assert numpy.all(img == img2)
|
||||
pam.close()
|
||||
except ValueError as e:
|
||||
print(fname, e)
|
||||
continue
|
||||
_shape = img.shape
|
||||
if img.ndim > 3 or (img.ndim > 2 and img.shape[-1] not in (3, 4)):
|
||||
img = img[0]
|
||||
cmap = 'gray' if pam.maxval > 1 else 'binary'
|
||||
pyplot.imshow(img, cmap, interpolation='nearest')
|
||||
pyplot.title("%s %s %s %s" % (fname, unicode(pam.magicnum),
|
||||
_shape, img.dtype))
|
||||
pyplot.show()
|
||||
32
GPy/plotting/matplot_dep/priors_plots.py
Normal file
32
GPy/plotting/matplot_dep/priors_plots.py
Normal file
|
|
@ -0,0 +1,32 @@
|
|||
# Copyright (c) 2012, GPy authors (see AUTHORS.txt).
|
||||
# Licensed under the BSD 3-clause license (see LICENSE.txt)
|
||||
|
||||
|
||||
import numpy as np
|
||||
try:
|
||||
import pylab as pb
|
||||
except:
|
||||
pass
|
||||
|
||||
|
||||
def univariate_plot(prior):
|
||||
rvs = prior.rvs(1000)
|
||||
pb.hist(rvs, 100, normed=True)
|
||||
xmin, xmax = pb.xlim()
|
||||
xx = np.linspace(xmin, xmax, 1000)
|
||||
pb.plot(xx, prior.pdf(xx), 'r', linewidth=2)
|
||||
|
||||
def plot(prior):
|
||||
|
||||
if prior.input_dim == 2:
|
||||
rvs = prior.rvs(200)
|
||||
pb.plot(rvs[:, 0], rvs[:, 1], 'kx', mew=1.5)
|
||||
xmin, xmax = pb.xlim()
|
||||
ymin, ymax = pb.ylim()
|
||||
xx, yy = np.mgrid[xmin:xmax:100j, ymin:ymax:100j]
|
||||
xflat = np.vstack((xx.flatten(), yy.flatten())).T
|
||||
zz = prior.pdf(xflat).reshape(100, 100)
|
||||
pb.contour(xx, yy, zz, linewidths=2)
|
||||
|
||||
else:
|
||||
raise NotImplementedError, "Cannot define a frame with more than two input dimensions"
|
||||
28
GPy/plotting/matplot_dep/ssgplvm.py
Normal file
28
GPy/plotting/matplot_dep/ssgplvm.py
Normal file
|
|
@ -0,0 +1,28 @@
|
|||
"""
|
||||
The module plotting results for SSGPLVM
|
||||
"""
|
||||
|
||||
import pylab
|
||||
|
||||
from ...models import SSGPLVM
|
||||
from img_plots import plot_2D_images
|
||||
|
||||
class SSGPLVM_plot(object):
|
||||
def __init__(self,model, imgsize):
|
||||
assert isinstance(model,SSGPLVM)
|
||||
self.model = model
|
||||
self.imgsize= imgsize
|
||||
assert model.Y.shape[1] == imgsize[0]*imgsize[1]
|
||||
|
||||
def plot_inducing(self):
|
||||
fig1 = pylab.figure()
|
||||
mean = self.model.posterior.mean
|
||||
arr = mean.reshape(*(mean.shape[0],self.imgsize[1],self.imgsize[0]))
|
||||
plot_2D_images(fig1, arr)
|
||||
fig1.gca().set_title('The mean of inducing points')
|
||||
|
||||
fig2 = pylab.figure()
|
||||
covar = self.model.posterior.covariance
|
||||
plot_2D_images(fig2, covar)
|
||||
fig2.gca().set_title('The variance of inducing points')
|
||||
|
||||
43
GPy/plotting/matplot_dep/svig_plots.py
Normal file
43
GPy/plotting/matplot_dep/svig_plots.py
Normal file
|
|
@ -0,0 +1,43 @@
|
|||
# Copyright (c) 2012, James Hensman and Nicolo' Fusi
|
||||
# Licensed under the BSD 3-clause license (see LICENSE.txt)
|
||||
|
||||
import numpy as np
|
||||
import pylab as pb
|
||||
|
||||
|
||||
def plot(model, ax=None, fignum=None, Z_height=None, **kwargs):
|
||||
|
||||
if ax is None:
|
||||
fig = pb.figure(num=fignum)
|
||||
ax = fig.add_subplot(111)
|
||||
|
||||
#horrible hack here:
|
||||
data = model.likelihood.data.copy()
|
||||
model.likelihood.data = model.Y
|
||||
GP.plot(model, ax=ax, **kwargs)
|
||||
model.likelihood.data = data
|
||||
|
||||
Zu = model.Z * model._Xscale + model._Xoffset
|
||||
if model.input_dim==1:
|
||||
ax.plot(model.X_batch, model.likelihood.data, 'gx',mew=2)
|
||||
if Z_height is None:
|
||||
Z_height = ax.get_ylim()[0]
|
||||
ax.plot(Zu, np.zeros_like(Zu) + Z_height, 'r|', mew=1.5, markersize=12)
|
||||
|
||||
if model.input_dim==2:
|
||||
ax.scatter(model.X[:,0], model.X[:,1], 20., model.Y[:,0], linewidth=0, cmap=pb.cm.jet) # @UndefinedVariable
|
||||
ax.plot(Zu[:,0], Zu[:,1], 'w^')
|
||||
|
||||
def plot_traces(model):
|
||||
|
||||
pb.figure()
|
||||
t = np.array(model._param_trace)
|
||||
pb.subplot(2,1,1)
|
||||
for l,ti in zip(model._get_param_names(),t.T):
|
||||
if not l[:3]=='iip':
|
||||
pb.plot(ti,label=l)
|
||||
pb.legend(loc=0)
|
||||
|
||||
pb.subplot(2,1,2)
|
||||
pb.plot(np.asarray(model._ll_trace),label='stochastic likelihood')
|
||||
pb.legend(loc=0)
|
||||
100
GPy/plotting/matplot_dep/variational_plots.py
Normal file
100
GPy/plotting/matplot_dep/variational_plots.py
Normal file
|
|
@ -0,0 +1,100 @@
|
|||
import pylab as pb, numpy as np
|
||||
|
||||
def plot(parameterized, fignum=None, ax=None, colors=None):
|
||||
"""
|
||||
Plot latent space X in 1D:
|
||||
|
||||
- if fig is given, create input_dim subplots in fig and plot in these
|
||||
- if ax is given plot input_dim 1D latent space plots of X into each `axis`
|
||||
- if neither fig nor ax is given create a figure with fignum and plot in there
|
||||
|
||||
colors:
|
||||
colors of different latent space dimensions input_dim
|
||||
|
||||
"""
|
||||
if ax is None:
|
||||
fig = pb.figure(num=fignum, figsize=(8, min(12, (2 * parameterized.mean.shape[1]))))
|
||||
if colors is None:
|
||||
colors = pb.gca()._get_lines.color_cycle
|
||||
pb.clf()
|
||||
else:
|
||||
colors = iter(colors)
|
||||
plots = []
|
||||
means, variances = parameterized.mean, parameterized.variance
|
||||
x = np.arange(means.shape[0])
|
||||
for i in range(means.shape[1]):
|
||||
if ax is None:
|
||||
a = fig.add_subplot(means.shape[1], 1, i + 1)
|
||||
elif isinstance(ax, (tuple, list)):
|
||||
a = ax[i]
|
||||
else:
|
||||
raise ValueError("Need one ax per latent dimension input_dim")
|
||||
a.plot(means, c='k', alpha=.3)
|
||||
plots.extend(a.plot(x, means.T[i], c=colors.next(), label=r"$\mathbf{{X_{{{}}}}}$".format(i)))
|
||||
a.fill_between(x,
|
||||
means.T[i] - 2 * np.sqrt(variances.T[i]),
|
||||
means.T[i] + 2 * np.sqrt(variances.T[i]),
|
||||
facecolor=plots[-1].get_color(),
|
||||
alpha=.3)
|
||||
a.legend(borderaxespad=0.)
|
||||
a.set_xlim(x.min(), x.max())
|
||||
if i < means.shape[1] - 1:
|
||||
a.set_xticklabels('')
|
||||
pb.draw()
|
||||
fig.tight_layout(h_pad=.01) # , rect=(0, 0, 1, .95))
|
||||
return fig
|
||||
|
||||
def plot_SpikeSlab(parameterized, fignum=None, ax=None, colors=None, side_by_side=True):
|
||||
"""
|
||||
Plot latent space X in 1D:
|
||||
|
||||
- if fig is given, create input_dim subplots in fig and plot in these
|
||||
- if ax is given plot input_dim 1D latent space plots of X into each `axis`
|
||||
- if neither fig nor ax is given create a figure with fignum and plot in there
|
||||
|
||||
colors:
|
||||
colors of different latent space dimensions input_dim
|
||||
|
||||
"""
|
||||
if ax is None:
|
||||
if side_by_side:
|
||||
fig = pb.figure(num=fignum, figsize=(16, min(12, (2 * parameterized.mean.shape[1]))))
|
||||
else:
|
||||
fig = pb.figure(num=fignum, figsize=(8, min(12, (2 * parameterized.mean.shape[1]))))
|
||||
if colors is None:
|
||||
colors = pb.gca()._get_lines.color_cycle
|
||||
pb.clf()
|
||||
else:
|
||||
colors = iter(colors)
|
||||
plots = []
|
||||
means, variances, gamma = parameterized.mean, parameterized.variance, parameterized.binary_prob
|
||||
x = np.arange(means.shape[0])
|
||||
for i in range(means.shape[1]):
|
||||
if side_by_side:
|
||||
sub1 = (means.shape[1],2,2*i+1)
|
||||
sub2 = (means.shape[1],2,2*i+2)
|
||||
else:
|
||||
sub1 = (means.shape[1]*2,1,2*i+1)
|
||||
sub2 = (means.shape[1]*2,1,2*i+2)
|
||||
|
||||
# mean and variance plot
|
||||
a = fig.add_subplot(*sub1)
|
||||
a.plot(means, c='k', alpha=.3)
|
||||
plots.extend(a.plot(x, means.T[i], c=colors.next(), label=r"$\mathbf{{X_{{{}}}}}$".format(i)))
|
||||
a.fill_between(x,
|
||||
means.T[i] - 2 * np.sqrt(variances.T[i]),
|
||||
means.T[i] + 2 * np.sqrt(variances.T[i]),
|
||||
facecolor=plots[-1].get_color(),
|
||||
alpha=.3)
|
||||
a.legend(borderaxespad=0.)
|
||||
a.set_xlim(x.min(), x.max())
|
||||
if i < means.shape[1] - 1:
|
||||
a.set_xticklabels('')
|
||||
# binary prob plot
|
||||
a = fig.add_subplot(*sub2)
|
||||
a.bar(x,gamma[:,i],bottom=0.,linewidth=0,width=1.0,align='center')
|
||||
a.set_xlim(x.min(), x.max())
|
||||
a.set_ylim([0.,1.])
|
||||
pb.draw()
|
||||
fig.tight_layout(h_pad=.01) # , rect=(0, 0, 1, .95))
|
||||
return fig
|
||||
562
GPy/plotting/matplot_dep/visualize.py
Normal file
562
GPy/plotting/matplot_dep/visualize.py
Normal file
|
|
@ -0,0 +1,562 @@
|
|||
import matplotlib.pyplot as plt
|
||||
from mpl_toolkits.mplot3d import Axes3D
|
||||
import GPy
|
||||
import numpy as np
|
||||
import matplotlib as mpl
|
||||
import time
|
||||
from GPy.core.parameterization.variational import VariationalPosterior
|
||||
try:
|
||||
import visual
|
||||
visual_available = True
|
||||
|
||||
except ImportError:
|
||||
visual_available = False
|
||||
|
||||
|
||||
class data_show:
|
||||
"""
|
||||
The data_show class is a base class which describes how to visualize a
|
||||
particular data set. For example, motion capture data can be plotted as a
|
||||
stick figure, or images are shown using imshow. This class enables latent
|
||||
to data visualizations for the GP-LVM.
|
||||
"""
|
||||
def __init__(self, vals):
|
||||
self.vals = vals.copy()
|
||||
# If no axes are defined, create some.
|
||||
|
||||
def modify(self, vals):
|
||||
raise NotImplementedError, "this needs to be implemented to use the data_show class"
|
||||
|
||||
def close(self):
|
||||
raise NotImplementedError, "this needs to be implemented to use the data_show class"
|
||||
|
||||
class vpython_show(data_show):
|
||||
"""
|
||||
the vpython_show class is a base class for all visualization methods that use vpython to display. It is initialized with a scene. If the scene is set to None it creates a scene window.
|
||||
"""
|
||||
|
||||
def __init__(self, vals, scene=None):
|
||||
data_show.__init__(self, vals)
|
||||
# If no axes are defined, create some.
|
||||
|
||||
if scene==None:
|
||||
self.scene = visual.display(title='Data Visualization')
|
||||
else:
|
||||
self.scene = scene
|
||||
|
||||
def close(self):
|
||||
self.scene.exit()
|
||||
|
||||
|
||||
|
||||
class matplotlib_show(data_show):
|
||||
"""
|
||||
the matplotlib_show class is a base class for all visualization methods that use matplotlib. It is initialized with an axis. If the axis is set to None it creates a figure window.
|
||||
"""
|
||||
def __init__(self, vals, axes=None):
|
||||
data_show.__init__(self, vals)
|
||||
# If no axes are defined, create some.
|
||||
|
||||
if axes==None:
|
||||
fig = plt.figure()
|
||||
self.axes = fig.add_subplot(111)
|
||||
else:
|
||||
self.axes = axes
|
||||
|
||||
def close(self):
|
||||
plt.close(self.axes.get_figure())
|
||||
|
||||
class vector_show(matplotlib_show):
|
||||
"""
|
||||
A base visualization class that just shows a data vector as a plot of
|
||||
vector elements alongside their indices.
|
||||
"""
|
||||
def __init__(self, vals, axes=None):
|
||||
matplotlib_show.__init__(self, vals, axes)
|
||||
#assert vals.ndim == 2, "Please give a vector in [n x 1] to plot"
|
||||
#assert vals.shape[1] == 1, "only showing a vector in one dimension"
|
||||
self.size = vals.size
|
||||
self.handle = self.axes.plot(np.arange(0, vals.size)[:, None], vals)[0]
|
||||
|
||||
def modify(self, vals):
|
||||
self.vals = vals.copy()
|
||||
xdata, ydata = self.handle.get_data()
|
||||
assert vals.size == self.size, "values passed into modify changed size! vals.size:{} != in.size:{}".format(vals.size, self.size)
|
||||
self.handle.set_data(xdata, self.vals)
|
||||
self.axes.figure.canvas.draw()
|
||||
|
||||
|
||||
class lvm(matplotlib_show):
|
||||
def __init__(self, vals, model, data_visualize, latent_axes=None, sense_axes=None, latent_index=[0,1], disable_drag=False):
|
||||
"""Visualize a latent variable model
|
||||
|
||||
:param model: the latent variable model to visualize.
|
||||
:param data_visualize: the object used to visualize the data which has been modelled.
|
||||
:type data_visualize: visualize.data_show type.
|
||||
:param latent_axes: the axes where the latent visualization should be plotted.
|
||||
"""
|
||||
if vals is None:
|
||||
if isinstance(model.X, VariationalPosterior):
|
||||
vals = model.X.mean.values
|
||||
else:
|
||||
vals = model.X.values
|
||||
if len(vals.shape)==1:
|
||||
vals = vals[None,:]
|
||||
matplotlib_show.__init__(self, vals, axes=latent_axes)
|
||||
|
||||
if isinstance(latent_axes,mpl.axes.Axes):
|
||||
self.cid = latent_axes.figure.canvas.mpl_connect('button_press_event', self.on_click)
|
||||
if not disable_drag:
|
||||
self.cid = latent_axes.figure.canvas.mpl_connect('motion_notify_event', self.on_move)
|
||||
self.cid = latent_axes.figure.canvas.mpl_connect('axes_leave_event', self.on_leave)
|
||||
self.cid = latent_axes.figure.canvas.mpl_connect('axes_enter_event', self.on_enter)
|
||||
else:
|
||||
self.cid = latent_axes[0].figure.canvas.mpl_connect('button_press_event', self.on_click)
|
||||
if not disable_drag:
|
||||
self.cid = latent_axes[0].figure.canvas.mpl_connect('motion_notify_event', self.on_move)
|
||||
self.cid = latent_axes[0].figure.canvas.mpl_connect('axes_leave_event', self.on_leave)
|
||||
self.cid = latent_axes[0].figure.canvas.mpl_connect('axes_enter_event', self.on_enter)
|
||||
|
||||
self.data_visualize = data_visualize
|
||||
self.model = model
|
||||
self.latent_axes = latent_axes
|
||||
self.sense_axes = sense_axes
|
||||
self.called = False
|
||||
self.move_on = False
|
||||
self.latent_index = latent_index
|
||||
self.latent_dim = model.input_dim
|
||||
self.disable_drag = disable_drag
|
||||
|
||||
# The red cross which shows current latent point.
|
||||
self.latent_values = vals
|
||||
self.latent_handle = self.latent_axes.plot([0],[0],'rx',mew=2)[0]
|
||||
self.modify(vals)
|
||||
self.show_sensitivities()
|
||||
|
||||
def modify(self, vals):
|
||||
"""When latent values are modified update the latent representation and ulso update the output visualization."""
|
||||
self.vals = vals.view(np.ndarray).copy()
|
||||
y = self.model.predict(self.vals)[0]
|
||||
self.data_visualize.modify(y)
|
||||
self.latent_handle.set_data(self.vals[0,self.latent_index[0]], self.vals[0,self.latent_index[1]])
|
||||
self.axes.figure.canvas.draw()
|
||||
|
||||
|
||||
def on_enter(self,event):
|
||||
pass
|
||||
def on_leave(self,event):
|
||||
pass
|
||||
|
||||
def on_click(self, event):
|
||||
if event.inaxes!=self.latent_axes: return
|
||||
if self.disable_drag:
|
||||
self.move_on = True
|
||||
self.called = True
|
||||
self.on_move(event)
|
||||
else:
|
||||
self.move_on = not self.move_on
|
||||
self.called = True
|
||||
|
||||
def on_move(self, event):
|
||||
if event.inaxes!=self.latent_axes: return
|
||||
if self.called and self.move_on:
|
||||
# Call modify code on move
|
||||
self.latent_values[:, self.latent_index[0]]=event.xdata
|
||||
self.latent_values[:, self.latent_index[1]]=event.ydata
|
||||
self.modify(self.latent_values)
|
||||
|
||||
def show_sensitivities(self):
|
||||
# A click in the bar chart axis for selection a dimension.
|
||||
if self.sense_axes != None:
|
||||
self.sense_axes.cla()
|
||||
self.sense_axes.bar(np.arange(self.model.input_dim), self.model.input_sensitivity(), color='b')
|
||||
|
||||
if self.latent_index[1] == self.latent_index[0]:
|
||||
self.sense_axes.bar(np.array(self.latent_index[0]), self.model.input_sensitivity()[self.latent_index[0]], color='y')
|
||||
self.sense_axes.bar(np.array(self.latent_index[1]), self.model.input_sensitivity()[self.latent_index[1]], color='y')
|
||||
|
||||
else:
|
||||
self.sense_axes.bar(np.array(self.latent_index[0]), self.model.input_sensitivity()[self.latent_index[0]], color='g')
|
||||
self.sense_axes.bar(np.array(self.latent_index[1]), self.model.input_sensitivity()[self.latent_index[1]], color='r')
|
||||
|
||||
self.sense_axes.figure.canvas.draw()
|
||||
|
||||
|
||||
class lvm_subplots(lvm):
|
||||
"""
|
||||
latent_axes is a np array of dimension np.ceil(input_dim/2),
|
||||
one for each pair of the latent dimensions.
|
||||
"""
|
||||
def __init__(self, vals, Model, data_visualize, latent_axes=None, sense_axes=None):
|
||||
self.nplots = int(np.ceil(Model.input_dim/2.))+1
|
||||
assert len(latent_axes)==self.nplots
|
||||
if vals==None:
|
||||
vals = Model.X[0, :]
|
||||
self.latent_values = vals
|
||||
|
||||
for i, axis in enumerate(latent_axes):
|
||||
if i == self.nplots-1:
|
||||
if self.nplots*2!=Model.input_dim:
|
||||
latent_index = [i*2, i*2]
|
||||
lvm.__init__(self, self.latent_vals, Model, data_visualize, axis, sense_axes, latent_index=latent_index)
|
||||
else:
|
||||
latent_index = [i*2, i*2+1]
|
||||
lvm.__init__(self, self.latent_vals, Model, data_visualize, axis, latent_index=latent_index)
|
||||
|
||||
|
||||
|
||||
class lvm_dimselect(lvm):
|
||||
"""
|
||||
A visualizer for latent variable models which allows selection of the latent dimensions to use by clicking on a bar chart of their length scales.
|
||||
|
||||
For an example of the visualizer's use try:
|
||||
|
||||
GPy.examples.dimensionality_reduction.BGPVLM_oil()
|
||||
|
||||
"""
|
||||
def __init__(self, vals, model, data_visualize, latent_axes=None, sense_axes=None, latent_index=[0, 1], labels=None):
|
||||
if latent_axes==None and sense_axes==None:
|
||||
self.fig,(latent_axes,self.sense_axes) = plt.subplots(1,2)
|
||||
elif sense_axes==None:
|
||||
fig=plt.figure()
|
||||
self.sense_axes = fig.add_subplot(111)
|
||||
else:
|
||||
self.sense_axes = sense_axes
|
||||
self.labels = labels
|
||||
lvm.__init__(self,vals,model,data_visualize,latent_axes,sense_axes,latent_index)
|
||||
self.show_sensitivities()
|
||||
print self.latent_values
|
||||
print "use left and right mouse buttons to select dimensions"
|
||||
|
||||
|
||||
def on_click(self, event):
|
||||
if event.inaxes==self.sense_axes:
|
||||
new_index = max(0,min(int(np.round(event.xdata-0.5)),self.model.input_dim-1))
|
||||
if event.button == 1:
|
||||
# Make it red if and y-axis (red=port=left) if it is a left button click
|
||||
self.latent_index[1] = new_index
|
||||
else:
|
||||
# Make it green and x-axis (green=starboard=right) if it is a right button click
|
||||
self.latent_index[0] = new_index
|
||||
|
||||
self.show_sensitivities()
|
||||
|
||||
self.latent_axes.cla()
|
||||
self.model.plot_latent(which_indices=self.latent_index,
|
||||
ax=self.latent_axes, labels=self.labels)
|
||||
self.latent_handle = self.latent_axes.plot([0],[0],'rx',mew=2)[0]
|
||||
self.modify(self.latent_values)
|
||||
|
||||
elif event.inaxes==self.latent_axes:
|
||||
self.move_on = not self.move_on
|
||||
|
||||
self.called = True
|
||||
|
||||
|
||||
|
||||
def on_leave(self,event):
|
||||
print type(self.latent_values)
|
||||
latent_values = self.latent_values.copy()
|
||||
y = self.model.predict(latent_values[None,:])[0]
|
||||
self.data_visualize.modify(y)
|
||||
|
||||
|
||||
|
||||
class image_show(matplotlib_show):
|
||||
"""Show a data vector as an image. This visualizer rehapes the output vector and displays it as an image.
|
||||
|
||||
:param vals: the values of the output to display.
|
||||
:type vals: ndarray
|
||||
:param axes: the axes to show the output on.
|
||||
:type vals: axes handle
|
||||
:param dimensions: the dimensions that the image needs to be transposed to for display.
|
||||
:type dimensions: tuple
|
||||
:param transpose: whether to transpose the image before display.
|
||||
:type bool: default is False.
|
||||
:param order: whether array is in Fortan ordering ('F') or Python ordering ('C'). Default is python ('C').
|
||||
:type order: string
|
||||
:param invert: whether to invert the pixels or not (default False).
|
||||
:type invert: bool
|
||||
:param palette: a palette to use for the image.
|
||||
:param preset_mean: the preset mean of a scaled image.
|
||||
:type preset_mean: double
|
||||
:param preset_std: the preset standard deviation of a scaled image.
|
||||
:type preset_std: double
|
||||
:param cmap: the colormap for image visualization
|
||||
:type cmap: matplotlib.cm"""
|
||||
|
||||
def __init__(self, vals, axes=None, dimensions=(16,16), transpose=False, order='C', invert=False, scale=False, palette=[], preset_mean=0., preset_std=1., select_image=0, cmap=None):
|
||||
matplotlib_show.__init__(self, vals, axes)
|
||||
self.dimensions = dimensions
|
||||
self.transpose = transpose
|
||||
self.order = order
|
||||
self.invert = invert
|
||||
self.scale = scale
|
||||
self.palette = palette
|
||||
self.preset_mean = preset_mean
|
||||
self.preset_std = preset_std
|
||||
self.select_image = select_image # This is used when the y vector contains multiple images concatenated.
|
||||
|
||||
self.set_image(self.vals)
|
||||
if not self.palette == []: # Can just show the image (self.set_image() took care of setting the palette)
|
||||
self.handle = self.axes.imshow(self.vals, interpolation='nearest')
|
||||
elif cmap==None: # Use a jet map.
|
||||
self.handle = self.axes.imshow(self.vals, cmap=plt.cm.jet, interpolation='nearest') # @UndefinedVariable
|
||||
else: # Use the selected map.
|
||||
self.handle = self.axes.imshow(self.vals, cmap=cmap, interpolation='nearest') # @UndefinedVariable
|
||||
plt.show()
|
||||
|
||||
def modify(self, vals):
|
||||
self.set_image(vals.copy())
|
||||
self.handle.set_array(self.vals)
|
||||
self.axes.figure.canvas.draw()
|
||||
|
||||
def set_image(self, vals):
|
||||
dim = self.dimensions[0] * self.dimensions[1]
|
||||
num_images = np.sqrt(vals[0,].size/dim)
|
||||
if num_images > 1 and num_images.is_integer(): # Show a mosaic of images
|
||||
num_images = np.int(num_images)
|
||||
self.vals = np.zeros((self.dimensions[0]*num_images, self.dimensions[1]*num_images))
|
||||
for iR in range(num_images):
|
||||
for iC in range(num_images):
|
||||
cur_img_id = iR*num_images + iC
|
||||
cur_img = np.reshape(vals[0,dim*cur_img_id+np.array(range(dim))], self.dimensions, order=self.order)
|
||||
first_row = iR*self.dimensions[0]
|
||||
last_row = (iR+1)*self.dimensions[0]
|
||||
first_col = iC*self.dimensions[1]
|
||||
last_col = (iC+1)*self.dimensions[1]
|
||||
self.vals[first_row:last_row, first_col:last_col] = cur_img
|
||||
|
||||
else:
|
||||
self.vals = np.reshape(vals[0,dim*self.select_image+np.array(range(dim))], self.dimensions, order=self.order)
|
||||
if self.transpose:
|
||||
self.vals = self.vals.T
|
||||
# if not self.scale:
|
||||
# self.vals = self.vals
|
||||
if self.invert:
|
||||
self.vals = -self.vals
|
||||
|
||||
# un-normalizing, for visualisation purposes:
|
||||
self.vals = self.vals*self.preset_std + self.preset_mean
|
||||
# Clipping the values:
|
||||
#self.vals[self.vals < 0] = 0
|
||||
#self.vals[self.vals > 255] = 255
|
||||
#else:
|
||||
#self.vals = 255*(self.vals - self.vals.min())/(self.vals.max() - self.vals.min())
|
||||
if not self.palette == []: # applying using an image palette (e.g. if the image has been quantized)
|
||||
from PIL import Image
|
||||
self.vals = Image.fromarray(self.vals.astype('uint8'))
|
||||
self.vals.putpalette(self.palette) # palette is a list, must be loaded before calling this function
|
||||
|
||||
class mocap_data_show_vpython(vpython_show):
|
||||
"""Base class for visualizing motion capture data using visual module."""
|
||||
|
||||
def __init__(self, vals, scene=None, connect=None, radius=0.1):
|
||||
vpython_show.__init__(self, vals, scene)
|
||||
self.radius = radius
|
||||
self.connect = connect
|
||||
self.process_values()
|
||||
self.draw_edges()
|
||||
self.draw_vertices()
|
||||
|
||||
def draw_vertices(self):
|
||||
self.spheres = []
|
||||
for i in range(self.vals.shape[0]):
|
||||
self.spheres.append(visual.sphere(pos=(self.vals[i, 0], self.vals[i, 2], self.vals[i, 1]), radius=self.radius))
|
||||
self.scene.visible=True
|
||||
|
||||
def draw_edges(self):
|
||||
self.rods = []
|
||||
self.line_handle = []
|
||||
if not self.connect==None:
|
||||
self.I, self.J = np.nonzero(self.connect)
|
||||
for i, j in zip(self.I, self.J):
|
||||
pos, axis = self.pos_axis(i, j)
|
||||
self.rods.append(visual.cylinder(pos=pos, axis=axis, radius=self.radius))
|
||||
|
||||
def modify_vertices(self):
|
||||
for i in range(self.vals.shape[0]):
|
||||
self.spheres[i].pos = (self.vals[i, 0], self.vals[i, 2], self.vals[i, 1])
|
||||
|
||||
def modify_edges(self):
|
||||
self.line_handle = []
|
||||
if not self.connect==None:
|
||||
self.I, self.J = np.nonzero(self.connect)
|
||||
for rod, i, j in zip(self.rods, self.I, self.J):
|
||||
rod.pos, rod.axis = self.pos_axis(i, j)
|
||||
|
||||
def pos_axis(self, i, j):
|
||||
pos = []
|
||||
axis = []
|
||||
pos.append(self.vals[i, 0])
|
||||
axis.append(self.vals[j, 0]-self.vals[i,0])
|
||||
pos.append(self.vals[i, 2])
|
||||
axis.append(self.vals[j, 2]-self.vals[i,2])
|
||||
pos.append(self.vals[i, 1])
|
||||
axis.append(self.vals[j, 1]-self.vals[i,1])
|
||||
return pos, axis
|
||||
|
||||
def modify(self, vals):
|
||||
self.vals = vals.copy()
|
||||
self.process_values()
|
||||
self.modify_edges()
|
||||
self.modify_vertices()
|
||||
|
||||
def process_values(self):
|
||||
raise NotImplementedError, "this needs to be implemented to use the data_show class"
|
||||
|
||||
class mocap_data_show(matplotlib_show):
|
||||
"""Base class for visualizing motion capture data."""
|
||||
|
||||
def __init__(self, vals, axes=None, connect=None):
|
||||
if axes==None:
|
||||
fig = plt.figure()
|
||||
axes = fig.add_subplot(111, projection='3d', aspect='equal')
|
||||
matplotlib_show.__init__(self, vals, axes)
|
||||
|
||||
self.connect = connect
|
||||
self.process_values()
|
||||
self.initialize_axes()
|
||||
self.draw_vertices()
|
||||
self.finalize_axes()
|
||||
self.draw_edges()
|
||||
self.axes.figure.canvas.draw()
|
||||
|
||||
def draw_vertices(self):
|
||||
self.points_handle = self.axes.scatter(self.vals[:, 0], self.vals[:, 1], self.vals[:, 2])
|
||||
|
||||
def draw_edges(self):
|
||||
self.line_handle = []
|
||||
if not self.connect==None:
|
||||
x = []
|
||||
y = []
|
||||
z = []
|
||||
self.I, self.J = np.nonzero(self.connect)
|
||||
for i, j in zip(self.I, self.J):
|
||||
x.append(self.vals[i, 0])
|
||||
x.append(self.vals[j, 0])
|
||||
x.append(np.NaN)
|
||||
y.append(self.vals[i, 1])
|
||||
y.append(self.vals[j, 1])
|
||||
y.append(np.NaN)
|
||||
z.append(self.vals[i, 2])
|
||||
z.append(self.vals[j, 2])
|
||||
z.append(np.NaN)
|
||||
self.line_handle = self.axes.plot(np.array(x), np.array(y), np.array(z), 'b-')
|
||||
|
||||
def modify(self, vals):
|
||||
self.vals = vals.copy()
|
||||
self.process_values()
|
||||
self.initialize_axes_modify()
|
||||
self.draw_vertices()
|
||||
self.initialize_axes()
|
||||
self.finalize_axes_modify()
|
||||
self.draw_edges()
|
||||
self.axes.figure.canvas.draw()
|
||||
|
||||
def process_values(self):
|
||||
raise NotImplementedError, "this needs to be implemented to use the data_show class"
|
||||
|
||||
def initialize_axes(self, boundary=0.05):
|
||||
"""Set up the axes with the right limits and scaling."""
|
||||
bs = [(self.vals[:, i].max()-self.vals[:, i].min())*boundary for i in xrange(3)]
|
||||
self.x_lim = np.array([self.vals[:, 0].min()-bs[0], self.vals[:, 0].max()+bs[0]])
|
||||
self.y_lim = np.array([self.vals[:, 1].min()-bs[1], self.vals[:, 1].max()+bs[1]])
|
||||
self.z_lim = np.array([self.vals[:, 2].min()-bs[2], self.vals[:, 2].max()+bs[2]])
|
||||
|
||||
def initialize_axes_modify(self):
|
||||
self.points_handle.remove()
|
||||
self.line_handle[0].remove()
|
||||
|
||||
def finalize_axes(self):
|
||||
self.axes.set_xlim(self.x_lim)
|
||||
self.axes.set_ylim(self.y_lim)
|
||||
self.axes.set_zlim(self.z_lim)
|
||||
self.axes.auto_scale_xyz([-1., 1.], [-1., 1.], [-1., 1.])
|
||||
|
||||
# self.axes.set_aspect('equal')
|
||||
# self.axes.autoscale(enable=False)
|
||||
|
||||
def finalize_axes_modify(self):
|
||||
self.axes.set_xlim(self.x_lim)
|
||||
self.axes.set_ylim(self.y_lim)
|
||||
self.axes.set_zlim(self.z_lim)
|
||||
|
||||
class stick_show(mocap_data_show):
|
||||
"""Show a three dimensional point cloud as a figure. Connect elements of the figure together using the matrix connect."""
|
||||
def __init__(self, vals, connect=None, axes=None):
|
||||
if len(vals.shape)==1:
|
||||
vals = vals[None,:]
|
||||
mocap_data_show.__init__(self, vals, axes=axes, connect=connect)
|
||||
|
||||
def process_values(self):
|
||||
self.vals = self.vals.reshape((3, self.vals.shape[1]/3)).T
|
||||
|
||||
class skeleton_show(mocap_data_show):
|
||||
"""data_show class for visualizing motion capture data encoded as a skeleton with angles."""
|
||||
def __init__(self, vals, skel, axes=None, padding=0):
|
||||
"""data_show class for visualizing motion capture data encoded as a skeleton with angles.
|
||||
:param vals: set of modeled angles to use for printing in the axis when it's first created.
|
||||
:type vals: np.array
|
||||
:param skel: skeleton object that has the parameters of the motion capture skeleton associated with it.
|
||||
:type skel: mocap.skeleton object
|
||||
:param padding:
|
||||
:type int
|
||||
"""
|
||||
self.skel = skel
|
||||
self.padding = padding
|
||||
connect = skel.connection_matrix()
|
||||
mocap_data_show.__init__(self, vals, axes=axes, connect=connect)
|
||||
def process_values(self):
|
||||
"""Takes a set of angles and converts them to the x,y,z coordinates in the internal prepresentation of the class, ready for plotting.
|
||||
|
||||
:param vals: the values that are being modelled."""
|
||||
|
||||
if self.padding>0:
|
||||
channels = np.zeros((self.vals.shape[0], self.vals.shape[1]+self.padding))
|
||||
channels[:, 0:self.vals.shape[0]] = self.vals
|
||||
else:
|
||||
channels = self.vals
|
||||
vals_mat = self.skel.to_xyz(channels.flatten())
|
||||
self.vals = np.zeros_like(vals_mat)
|
||||
# Flip the Y and Z axes
|
||||
self.vals[:, 0] = vals_mat[:, 0].copy()
|
||||
self.vals[:, 1] = vals_mat[:, 2].copy()
|
||||
self.vals[:, 2] = vals_mat[:, 1].copy()
|
||||
|
||||
def wrap_around(self, lim, connect):
|
||||
quot = lim[1] - lim[0]
|
||||
self.vals = rem(self.vals, quot)+lim[0]
|
||||
nVals = floor(self.vals/quot)
|
||||
for i in range(connect.shape[0]):
|
||||
for j in find(connect[i, :]):
|
||||
if nVals[i] != nVals[j]:
|
||||
connect[i, j] = False
|
||||
return connect
|
||||
|
||||
|
||||
def data_play(Y, visualizer, frame_rate=30):
|
||||
"""Play a data set using the data_show object given.
|
||||
|
||||
:Y: the data set to be visualized.
|
||||
:param visualizer: the data show objectwhether to display during optimisation
|
||||
:type visualizer: data_show
|
||||
|
||||
Example usage:
|
||||
|
||||
This example loads in the CMU mocap database (http://mocap.cs.cmu.edu) subject number 35 motion number 01. It then plays it using the mocap_show visualize object.
|
||||
|
||||
.. code-block:: python
|
||||
|
||||
data = GPy.util.datasets.cmu_mocap(subject='35', train_motions=['01'])
|
||||
Y = data['Y']
|
||||
Y[:, 0:3] = 0. # Make figure walk in place
|
||||
visualize = GPy.util.visualize.skeleton_show(Y[0, :], data['skel'])
|
||||
GPy.util.visualize.data_play(Y, visualize)
|
||||
|
||||
"""
|
||||
|
||||
|
||||
for y in Y:
|
||||
visualizer.modify(y[None, :])
|
||||
time.sleep(1./float(frame_rate))
|
||||
Loading…
Add table
Add a link
Reference in a new issue