介绍pandas模块用于数据表分类汇总和导出。
承接上文,我们对每个数据的计算中间结果都存放到一个字典中,再把多个数据 item 放到一个列表 box 中。接下来就需要收集我们所有的计算结果,整合到一个数据表(dataframe),以便汇总分析。具体代码如下:
data = []
for item in box:
print(item['img_fp'], len(item['values']))
df = pd.DataFrame()
df['intensity'] = item['values']
df['img_id'] = item['img_id']
df['group'] = item['group']
df['cell'] = item['cell']
data.append(df)
data = pd.concat(data, ignore_index=True)
# 保存中间数据,以备不时之需
with open('data3.pkl', 'wb') as f:
pickle.dump(data, f)
这里就是一个循环遍历,访问每个数据 item,从中提取出我们想要的信息,然后写入一个 dataframe。
需要注意的是,由于 item['values']
是数值,而 group
还有 cell
这些都是字符串类型。而且长度还不一致。所以这里创建了一个空白 dataframe (变量名为 df)之后,首选填充 item['values']
,这个 dataframe 的长度就和 values 一致,然后再赋值其它的非数值列,会自动补齐长度。但是这个 dataframe 中的 values 列已经发生了类型转化,从数值变为了文本,后面也是需要注意的。
每个数据 item 都会得到一个 dataframe,然后我们使用一个列表把它们收集起来,遍历结束后使用 pd.concat
方法将这些 dataframe 合并成一张数据表就行。
接下来我们要计算每种细胞的信噪比,就会变得很方便。如下所示:
gps = data.groupby('cell')
pig = []
for cell, df in gps:
print(cell, '======')
gp1 = df.groupby("group")
a = gp1.get_group('u1')
b = gp1.get_group('ctrl')
res = calculateSNR(a, b)
pig.append(res)
这段代码中,先按dataframe 中 cell
列进行分组,然后对每种 cell 进行遍历,此时得到的是每个 cell 下所有的数据,然后进一步按 group
分组,得到信号和背景的数据,进而计算信噪比,其结果使用列表收集起来(请忽视示例中随性的列表命名)。
但是这个pig 列表收到的到都是一个个的字典,还需要进一步整合成我们习惯看的表格。这个可以通过下方代码实现:
# 整理到一个summary的表格
pig2 = [pd.Series(x) for x in pig]
pig3 = pd.concat(pig2, axis=1)
pig3.columns = ['7701', 'hpeg2', 'mhcc97']
pig3.to_excel("SNR_summary.xlsx")
这里首先使用 pd.Series
方法将字典转换下对象,原先的字典的 keys 会变为 pd.Series 的 index。再然后我们继续使用 pd.concat
方法把所有的 pd.Series 合并,注意 pd.concat
默认方向是纵向(axis=0, add row),这里的合并方向是横向(axis=1, add column)。合并之后,注意给 column 命名。这个汇总的结果可以保存为 excel 方便查看。
如果要对中间数据做一些直方图,可能要需要保存每个细胞不同条件下的数据表,则可以通过以下代码:
import pickle
import pandas as pd
with open('data3.pkl', 'rb') as f:
data = pickle.load(f)
gps = data.groupby('cell')
for cell, df in gps:
gp1 = df.groupby("group")
for group, df1 in gp1:
gp2 = df1.groupby("img_id")
for pid, df2 in gp2:
df2.to_csv(f'{cell}_{group}_{pid}.csv', index=None)
此处评论已关闭