<h3>如何创建气泡大小正确且无重叠的图形</h3>
<p>Seaborn <a href="https://seaborn.pydata.org/generated/seaborn.stripplot.html" rel="nofollow noreferrer">^{<cd1>}</a>和<a href="https://seaborn.pydata.org/generated/seaborn.stripplot.html" rel="nofollow noreferrer">^{<cd2>}</a>(或<code>sns.catplot(kind=strip or kind=swarm)</code>)提供了方便的<code>dodge</code>参数,防止气泡重叠。唯一的缺点是<code>size</code>参数将单个大小应用于所有气泡,而<code>sizes</code>参数(在另一个答案中使用)在这里没有用处。它们不像<a href="https://seaborn.pydata.org/generated/seaborn.scatterplot.html" rel="nofollow noreferrer">^{<cd9>}</a>的<code>s</code>和<code>size</code>参数那样工作。因此,生成绘图后,必须编辑每个气泡的大小:</p>
<pre><code>import numpy as np # v 1.19.2
import pandas as pd # v 1.1.3
import seaborn as sns # v 0.11.0
# Create sample data
x = ['IEEE', 'Elsevier', 'Others', 'IEEE', 'Elsevier', 'Others']
y = np.array([7, 6, 3, 7, 1, 3])
z = ['conference', 'conference', 'conference', 'journal', 'journal', 'journal']
df = pd.DataFrame(dict(organisation=x, count=y, category=z))
# Create seaborn stripplot (swarmplot can be used the same way)
ax = sns.stripplot(data=df, x='organisation', y='count', hue='category', dodge=True)
# Adjust the size of the bubbles
for coll in ax.collections[:-2]:
y = coll.get_offsets()[0][1]
coll.set_sizes([100*y])
# Format figure size, spines and grid
ax.figure.set_size_inches(7, 5)
ax.grid(axis='y', color='black', alpha=0.2)
ax.grid(axis='x', which='minor', color='black', alpha=0.2)
ax.spines['bottom'].set(position='zero', color='black', alpha=0.2)
sns.despine(left=True)
# Format ticks
ax.tick_params(axis='both', length=0, pad=10, labelsize=12)
ax.tick_params(axis='x', which='minor', length=25, width=0.8, color=[0, 0, 0, 0.2])
minor_xticks = [tick+0.5 for tick in ax.get_xticks() if tick != ax.get_xticks()[-1]]
ax.set_xticks(minor_xticks, minor=True)
ax.set_yticks(range(0, df['count'].max()+2))
# Edit labels and legend
ax.set_xlabel('Organisation', labelpad=15, size=12)
ax.set_ylabel('No. of Papers', labelpad=15, size=12)
ax.legend(bbox_to_anchor=(1.0, 0.5), loc='center left', frameon=False);
</code></pre>
<p><a href="https://i.stack.imgur.com/lHYVI.png" rel="nofollow noreferrer"><img src="https://i.stack.imgur.com/lHYVI.png" alt="stripplot"/></a></p>
<br/>
<p>或者,您可以将<code>scatterplot</code>与方便的<code>s</code>参数(或<code>size</code>)一起使用,然后编辑气泡之间的空间,以重现缺少的<code>dodge</code>参数的效果(注意<code>x_jitter</code>参数似乎没有效果)。下面是一个示例,使用与以前相同的数据,但没有所有额外的格式:</p>
<pre><code># Create seaborn scatterplot with size argument
ax = sns.scatterplot(data=df, x='organisation', y='count',
hue='category', s=100*df['count'])
ax.figure.set_size_inches(7, 5)
ax.margins(0.2)
# Dodge bubbles
bubbles = ax.collections[0].get_offsets()
signs = np.repeat([-1, 1], df['organisation'].nunique())
for bubble, sign in zip(bubbles, signs):
bubble[0] += sign*0.15
</code></pre>
<p><a href="https://i.stack.imgur.com/a7sIh.png" rel="nofollow noreferrer"><img src="https://i.stack.imgur.com/a7sIh.png" alt="scatterplot"/></a></p>
<br/>
<br/>
<hr/>
<P>作为一个旁注,我建议您考虑其他类型的数据。分组条形图:</p>
<pre><code>df.pivot(index='organisation', columns='category').plot.bar()
</code></pre>
<p>或<a href="https://stackoverflow.com/a/50400060/14148248">balloon plot</a>(又称分类气泡图):</p>
<pre><code>sns.scatterplot(data=df, x='organisation', y='category', s=100*count).margins(0.4)
</code></pre>
<p><strong>为什么?</strong>在气泡图中,计数使用两个视觉属性显示,i)y坐标位置和ii)气泡大小。其中只有一个是真正必要的</p>