Seaborn catplot combined with PairGrid

2024/7/27 12:13:19

I am playing with the Titanic dataset, and trying to produce a pair plot of numeric variables against categorical variables. I can use Seaborn's catplot to graph a plot of one numeric variable against one categorical variable:

import seaborn as snssns.catplot(data=train, x='Fare', y='Sex')

However, if I try to use PairGrid to graph numeric variables against categorical variables:

x_vars = ['Fare']
y_vars = ['Sex']g = sns.PairGrid(train, x_vars=x_vars, y_vars=y_vars)
g.map(sns.catplot)

It fails with an error:

---------------------------------------------------------------------------
TypeError                                 Traceback (most recent call last)
<ipython-input-75-c284a7cfd727> in <module>9 #g.map_diag(lambda x, **kwargs: sns.catplot(x, x, **kwargs), jitter=True, kind="bar")10 #g.map(sns.scatterplot, y_jitter=1)#, hue=train["Survived"])
---> 11 g.map(sns.catplot)#, hue=train["Survived"])~/MLProject/book1/lib/python3.8/site-packages/seaborn/axisgrid.py in map(self, func, **kwargs)1363         row_indices, col_indices = np.indices(self.axes.shape)1364         indices = zip(row_indices.flat, col_indices.flat)
-> 1365         self._map_bivariate(func, indices, **kwargs)1366         return self1367 ~/MLProject/book1/lib/python3.8/site-packages/seaborn/axisgrid.py in _map_bivariate(self, func, indices, **kwargs)1504             y_var = self.y_vars[i]1505             ax = self.axes[i, j]
-> 1506             self._plot_bivariate(x_var, y_var, ax, func, kw_color, **kws)1507         self._add_axis_labels()1508 ~/MLProject/book1/lib/python3.8/site-packages/seaborn/axisgrid.py in _plot_bivariate(self, x_var, y_var, ax, func, kw_color, **kwargs)1534             color = self.palette[k] if kw_color is None else kw_color1535 
-> 1536             func(x, y, label=label_k, color=color, **kwargs)1537 1538         self._clean_axis(ax)~/MLProject/book1/lib/python3.8/site-packages/seaborn/categorical.py in catplot(x, y, hue, data, row, col, col_wrap, estimator, ci, n_boot, units, seed, order, hue_order, row_order, col_order, kind, height, aspect, orient, color, palette, legend, legend_out, sharex, sharey, margin_titles, facet_kws, **kwargs)3760 3761     # Initialize the facets
-> 3762     g = FacetGrid(**facet_kws)3763 3764     # Draw the plot onto the facets~/MLProject/book1/lib/python3.8/site-packages/seaborn/axisgrid.py in __init__(self, data, row, col, hue, col_wrap, sharex, sharey, height, aspect, palette, row_order, col_order, hue_order, hue_kws, dropna, legend_out, despine, margin_titles, xlim, ylim, subplot_kws, gridspec_kws, size)268         # Make a boolean mask that is True anywhere there is an NA269         # value in one of the faceting variables, but only if dropna is True
--> 270         none_na = np.zeros(len(data), np.bool)271         if dropna:272             row_na = none_na if row is None else data[row].isnull()TypeError: object of type 'NoneType' has no len()

If I replace g.map(sns.catplot) with g.map(sns.scatterplot) it does graph successfully without error.

How can I combine catplot with PairGrid?

Answer

@ImportanceOfBeingErnest already gave the right answer in a comment above: It does not make sense to combine sns.catplot() with a separately created FacetGrid, because sns.catplot() creates its own FacetGrid when called.

In any case, sns.catplot() invokes another seaborn function to do the actual plotting in each cell of the grid. That function can be selected by specifying the kind keyword argument to sns.catplot(). The default is kind="strip".

So if you want to manually create a FacetGrid and then map sns.catplot() to it, but without specifying the kind, you may as well use sns.stripplot() instead. This does work, but the Titanic dataset is too large for stripplots to be very informative, so I would use violin plots instead:

import seaborn as sns
sns.set()titanic = sns.load_dataset('titanic')num_vars = ['age', 'fare']
cat_vars = ['pclass', 'embarked', 'sex']g = sns.PairGrid(data=titanic, x_vars=cat_vars, y_vars=num_vars)
g.map(sns.violinplot)

facet violin plots

See the sns.catplot() documentation for more details.


Follow-up question by @Bjarne Thorsted: How to replace the boxplots inside the violinplots with swarmplots?

You can still use the same approach, just in this case calling g.map() twice. To change the default parameters of the plotting functions to be passed to g.map(), you can define modified versions of those functions using the * and ** operators:

import seaborn as sns
sns.set()titanic = sns.load_dataset('titanic')num_vars = ['age', 'fare']
cat_vars = ['pclass', 'embarked', 'sex']def violin_empty(*args, **kwargs):kwargs['color'] = 'lightblue'return sns.violinplot(*args, **kwargs, inner=None)def swarm_small(*args, **kwargs):kwargs['color'] = 'black'return sns.swarmplot(*args, **kwargs, size=1) g = sns.PairGrid(data=titanic, x_vars=cat_vars, y_vars=num_vars)
g.map(violin_empty)
g.map(swarm_small)

violinplots with swarmplots inside

https://en.xdnf.cn/q/73280.html

Related Q&A

Control individual linewidths in seaborn heatmap

Is it possible to widen the linewidth for sepcific columns and rows in a seaborn heatmap?For example, can this heatmapimport numpy as np; np.random.seed(0) import seaborn as sns; sns.set() uniform_dat…

openerp context in act_window

In OpenERP 6.1 this act_window:<act_windowdomain="[(id, =, student)]"id="act_schedule_student"name="Student"res_model="school.student"src_model="school.s…

Djangos redirects app doesnt work with URL parameters

I recently installed Djangos default redirects app on my site using the exact instructions specified:Ensured django.contrib.sites framework is installed. Added django.contrib.redirects to INSTALLED_APP…

get fully qualified method name from inspect stack

I have trouble completing the following function:def fullyQualifiedMethodNameInStack(depth=1):"""The function should return <file>_<class>_<method> for the method in th…

Project Euler #18 - how to brute force all possible paths in tree-like structure using Python?

Am trying to learn Python the Atlantic way and am stuck on Project Euler #18.All of the stuff I can find on the web (and theres a LOT more googling that happened beyond that) is some variation on well …

Is it possible to sniff the Character encoding?

I have a webpage that accepts CSV files. These files may be created in a variety of places. (I think) there is no way to specify the encoding in a CSV file - so I can not reliably treat all of them as …

numpy.empty giving nonempty array

When I create an empty numpy array using foo = np.empty(1) the resulting array contains a float64:>>> foo = np.empty(1) >>> foo array([ 0.]) >>> type(foo[0]) <type numpy.f…

Accessing password protected url from python script

In python, I want to send a request to a url which will return some information to me. The problem is if I try to access the url from the browser, a popup box appears and asks for a username and passwo…

Solving multiple linear sparse matrix equations: numpy.linalg.solve vs. scipy.sparse.linalg.spsolve

I have to solve a large amount of linear matrix equations of the type "Ax=B" for x where A is a sparse matrix with mainly the main diagonal populated and B is a vector. My first approach was …

I want to return html in a flask route [duplicate]

This question already has answers here:Python Flask Render Text from Variable like render_template(4 answers)Closed 6 years ago.Instead of using send_static_file, I want to use something like html(<…