微信公众号搜"智元新知"关注
微信扫一扫可直接关注哦!

单个单元格中多个数据的相关分析

如何解决单个单元格中多个数据的相关分析

我有一个数据集,其中一些行包含单一答案,而另一些行包含多个答案。像这样:

       year  length  Animation
0      1971     121       1,2,3
1      1939      71       1,3
2      1941       7       0,2
3      1996      70       1,0
4      1975      71       3,0

通过单一答案,我设法使用 df.corr() 创建了一个热图,但我无法弄清楚多行答案的最佳方法是什么。

我可以拆分它们并为每个答案添加额外的列,例如:

           year  length  Animation
    0      1971     121       1
    1      1971     121       2
    2      1971     121       3
    3      1939      71       1
    4      1939      71       3 ...

后执行完全相同的 dr.corr(),或添加额外的 Animation_01、Animation_02 ... 列,但必须有更聪明的方法解决此问题吗?

编辑:实际数据片段

Actual data snippet

解决方法

您应该使用 pd.crosstab() 计算两个分类变量之间的频率表,并基于此表执行后续分析。当 df.corr(x,y)x 之一是分类时,y 在数学上没有意义,无论是否编码为数字。

N.B.1 如果 x 是分类的,而 y 是数字的,有两个选项可以描述它们之间的联系:

  1. y 分组为分位数(bins)并将其视为分类的
  2. y 的单热编码虚拟变量执行 x 的线性回归

选项 2 总体上更精确,但统计数据超出了本问题的范围。这篇文章将重点讨论两个分类变量的情况。

N.B.2 对于稀疏矩阵输出,请参见 this post

示例解决方案

数据和预处理

import pandas as pd
import io
import matplotlib.pyplot as plt
from seaborn import heatmap

df = pd.read_csv(io.StringIO("""
       year  length  Animation
0      1971     121       1,2,3
1      1939      71       1,3
2      1941       7       0,2
3      1996      70       1,0
4      1975      71       3,0
"""),sep=r"\s{2,}",engine="python")

# convert string to list
df["Animation"] = df["Animation"].str.split(',')
# expand list column into new rows
df = df.explode("Animation")
# (optional)
df["Animation"] = df["Animation"].astype(int)

频率表

注意:为简单起见,忽略 length 的分组

ct = pd.crosstab(df["Animation"],df["length"])

print(ct)
# Out[65]:
# length     7    70   71   121
# Animation
# 0            1    1    1    0
# 1            0    1    1    1
# 2            1    1    1    1
# 3            0    0    2    1

可视化

ax = heatmap(ct,cmap="viridis",yticklabels=df["Animation"].drop_duplicates().sort_values(),xticklabels=df["length"].drop_duplicates().sort_values(),)
ax.set_title("Title",fontsize=20)
plt.show()

heatmap

示例分析

根据频率表,您可以询问给定某个(子集)y 值的 x 的分布,反之亦然。这应该更好地描述两个分类变量之间的联系,因为分类变量没有顺序。

例如

Q: What length does Animation=3 produces? 

A: 66.7% chance to give 71
   33.3% chance to give 121
   otherwise unobserved
,

您希望将 Animation(或数据片段中的 Preferred_positions)分解为一系列单热列,原始列中的每个唯一字符串对应一个单热列。具有 0 或 1 的每一列的值,一个对应于该字符串出现在原始列中的行。

首先,您需要获取 Preferred_positions 中的所有唯一子字符串(有关如何处理一列列表的信息,请参阅此 answer)。

positions = df.Preferred_positions.str.split(',').sum().unique()

然后,您可以根据给定的位置是否在每行的 Preferred_positions 中,在循环中创建位置列。

for position in positions:
    df[position] = df.Preferred_positions.apply(
        lambda x: 1 if position in x else 0
    )

版权声明:本文内容由互联网用户自发贡献,该文观点与技术仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 dio@foxmail.com 举报,一经查实,本站将立刻删除。