考虑一些钻孔中单个测试的数据框tests
:
borehole depthTest
0 B-1 1.5
1 B-1 20.0
2 B-42 1.0
3 B-42 2.0
4 B-42 15.0
5 B-42 30.0
6 B-09 1.0
7 B-09 10.0
8 B-09 15.0
我有另一个数据框liths
,每个钻孔的岩性范围:
borehole depthTop lith
0 B-1 0 sand
1 B-1 5 clay
2 B-1 18 shale
3 B-42 0 sand
4 B-42 1 clay
5 B-42 26 shale
6 B-09 0 sand
7 B-09 12 shale
岩性是每个钻孔的连续序列。例如:在B-1中,沙子的深度为0至5米,粘土为5至18米,页岩距离为18米。每个岩性的底部是下一个的顶部。换句话说,每个岩性的底部都是liths.groupby('borehole').depthTop.shift(-1)
编辑:我想加入两个dfs,这样我就可以得到每个测试的岩性:我想匹配borehole
,然后找到lith
最近的depthTop
< = depthTest
。
例如:在B-42中,粘土的深度为1米至26米。 B-42在15.0米处的试验应归类为粘土,因为15在1至26之间。
这是理想的结果:
borehole depthTest lith
0 B-1 1.5 sand
1 B-1 20.0 shale
2 B-42 1.0 clay
3 B-42 2.0 clay
4 B-42 15.0 clay
5 B-42 30.0 shale
6 B-09 1.0 sand
7 B-09 10.0 sand
8 B-09 15.0 shale
这似乎是groupby
和merge_asof
问题,但我无法弄清楚如何将它们组合在一起。
到目前为止,我的解决方案是将其转储到sqlite3
然后进行between
加入(就像我做here),但这真的好像失败了。< / p>
答案 0 :(得分:1)
在df2
上找到最接近的值并进行分类:
def logic(k):
vals = df2.loc[df2.borehole == k.borehole,:]
return vals[vals.depthTop == max(vals[vals.depthTop <= k.depthTest].depthTop)].lith.item()
df.transform(logic, 1)
0 sand
1 shale
2 clay
3 clay
4 clay
5 shale
6 sand
7 sand
8 shale
答案 1 :(得分:1)
让我们试试这个:
tests['lith'] = tests.groupby('borehole')['depthTest'].transform(lambda x: pd.cut(x,
bins = liths.loc[liths.borehole == x.name,'depthTop'].values.tolist() + [np.inf],
labels=liths.loc[liths.borehole == x.name,'lith'], right=False))
输出:
borehole depthTest lith
0 B-1 1.5 sand
1 B-1 20.0 shale
2 B-42 1.0 clay
3 B-42 2.0 clay
4 B-42 15.0 clay
5 B-42 30.0 shale
6 B-09 1.0 sand
7 B-09 10.0 sand
8 B-09 15.0 shale
让我们使用pd.cut
来标记范围内的值
并且通过使用groupby从井中获取岩石数据框中bins
和labels
的{{1}}。