gpt4 book ai didi

python - 用 Python 绘制双箱线图(2 轴箱线图;箱线图相关图)

转载 作者:行者123 更新时间:2023-12-01 08:33:06 26 4
gpt4 key购买 nike

我想在 x 轴和 y 轴上使用箱线图绘制两个变量的分布。我希望获得的图表示例可以在 site 上找到。但他们正在使用 R。

我想知道是否有可能在Python中使用matlplotlib.pyplot获得相同的结果。 boxplot 函数似乎不适用于这种图表。

我为两组尝试了类似的方法:

import matplotlib.pyplot as plt
x1 = [x11, x12, ..., x1n]
x2 = [x21, x22, ..., x2n]
y1 = [y11, y12, ..., y1n]
y2 = [y21, y22, ..., y2n]

data = [list(zip(x1,y1)), list(zip(x2,y2))]
fig, ax = plt.subplots()
ax.boxplot(data)

结果如下:而不是这样的:

最佳答案

这是使用 numpys percentile 方法和 RectangleLine2D 解决问题的粗略尝试实际绘图:

from matplotlib import pyplot as plt
from matplotlib.patches import Rectangle
from matplotlib.lines import Line2D

import numpy as np

def boxplot_2d(x,y, ax, whis=1.5):
xlimits = [np.percentile(x, q) for q in (25, 50, 75)]
ylimits = [np.percentile(y, q) for q in (25, 50, 75)]

##the box
box = Rectangle(
(xlimits[0],ylimits[0]),
(xlimits[2]-xlimits[0]),
(ylimits[2]-ylimits[0]),
ec = 'k',
zorder=0
)
ax.add_patch(box)

##the x median
vline = Line2D(
[xlimits[1],xlimits[1]],[ylimits[0],ylimits[2]],
color='k',
zorder=1
)
ax.add_line(vline)

##the y median
hline = Line2D(
[xlimits[0],xlimits[2]],[ylimits[1],ylimits[1]],
color='k',
zorder=1
)
ax.add_line(hline)

##the central point
ax.plot([xlimits[1]],[ylimits[1]], color='k', marker='o')

##the x-whisker
##defined as in matplotlib boxplot:
##As a float, determines the reach of the whiskers to the beyond the
##first and third quartiles. In other words, where IQR is the
##interquartile range (Q3-Q1), the upper whisker will extend to
##last datum less than Q3 + whis*IQR). Similarly, the lower whisker
####will extend to the first datum greater than Q1 - whis*IQR. Beyond
##the whiskers, data are considered outliers and are plotted as
##individual points. Set this to an unreasonably high value to force
##the whiskers to show the min and max values. Alternatively, set this
##to an ascending sequence of percentile (e.g., [5, 95]) to set the
##whiskers at specific percentiles of the data. Finally, whis can
##be the string 'range' to force the whiskers to the min and max of
##the data.
iqr = xlimits[2]-xlimits[0]

##left
left = np.min(x[x > xlimits[0]-whis*iqr])
whisker_line = Line2D(
[left, xlimits[0]], [ylimits[1],ylimits[1]],
color = 'k',
zorder = 1
)
ax.add_line(whisker_line)
whisker_bar = Line2D(
[left, left], [ylimits[0],ylimits[2]],
color = 'k',
zorder = 1
)
ax.add_line(whisker_bar)

##right
right = np.max(x[x < xlimits[2]+whis*iqr])
whisker_line = Line2D(
[right, xlimits[2]], [ylimits[1],ylimits[1]],
color = 'k',
zorder = 1
)
ax.add_line(whisker_line)
whisker_bar = Line2D(
[right, right], [ylimits[0],ylimits[2]],
color = 'k',
zorder = 1
)
ax.add_line(whisker_bar)

##the y-whisker
iqr = ylimits[2]-ylimits[0]

##bottom
bottom = np.min(y[y > ylimits[0]-whis*iqr])
whisker_line = Line2D(
[xlimits[1],xlimits[1]], [bottom, ylimits[0]],
color = 'k',
zorder = 1
)
ax.add_line(whisker_line)
whisker_bar = Line2D(
[xlimits[0],xlimits[2]], [bottom, bottom],
color = 'k',
zorder = 1
)
ax.add_line(whisker_bar)

##top
top = np.max(y[y < ylimits[2]+whis*iqr])
whisker_line = Line2D(
[xlimits[1],xlimits[1]], [top, ylimits[2]],
color = 'k',
zorder = 1
)
ax.add_line(whisker_line)
whisker_bar = Line2D(
[xlimits[0],xlimits[2]], [top, top],
color = 'k',
zorder = 1
)
ax.add_line(whisker_bar)

##outliers
mask = (x<left)|(x>right)|(y<bottom)|(y>top)
ax.scatter(
x[mask],y[mask],
facecolors='none', edgecolors='k'
)

#the figure and axes
fig,(ax1,ax2) = plt.subplots(ncols=2)

#some fake data
x = np.random.rand(1000)**2
y = np.sqrt(np.random.rand(1000))
#x = np.random.rand(1000)
#y = np.random.rand(1000)

#plotting the original data
ax1.scatter(x,y,c='r', s=1)

#doing the box plot
boxplot_2d(x,y,ax=ax2, whis=1)

plt.show()

当然,通过允许关键字参数,然后可以将其转发到 RectangleLine2D 调用,这当然仍然可以变得更好。最终结果如下所示:

Result of the above code

左侧以散点图形式显示实际数据,右侧显示生成的二维箱线图。希望这会有所帮助。

关于python - 用 Python 绘制双箱线图(2 轴箱线图;箱线图相关图),我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/53849636/

26 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com