Pandas合并(concat):ValueError:传递的值的形状为blah,索引暗示着blah2。

124

我正在尝试合并一个(Pandas 14.1)数据框和一个序列。该序列应该形成一个新的列,并且有一些NAs(因为序列的索引值是数据框索引值的子集)。

这对于一个玩具示例可以工作,但对于我的数据(如下所述)则不起作用。

示例:

import pandas as pd
import numpy as np

df1 = pd.DataFrame(np.random.randn(6, 4), columns=['A', 'B', 'C', 'D'], index=pd.date_range('1/1/2011', periods=6, freq='D'))
df1

A   B   C   D
2011-01-01  -0.487926   0.439190    0.194810    0.333896
2011-01-02  1.708024    0.237587    -0.958100   1.418285
2011-01-03  -1.228805   1.266068    -1.755050   -1.476395
2011-01-04  -0.554705   1.342504    0.245934    0.955521
2011-01-05  -0.351260   -0.798270   0.820535    -0.597322
2011-01-06  0.132924    0.501027    -1.139487   1.107873

s1 = pd.Series(np.random.randn(3), name='foo', index=pd.date_range('1/1/2011', periods=3, freq='2D'))
s1

2011-01-01   -1.660578
2011-01-03   -0.209688
2011-01-05    0.546146
Freq: 2D, Name: foo, dtype: float64

pd.concat([df1, s1],axis=1)

A   B   C   D   foo
2011-01-01  -0.487926   0.439190    0.194810    0.333896    -1.660578
2011-01-02  1.708024    0.237587    -0.958100   1.418285    NaN
2011-01-03  -1.228805   1.266068    -1.755050   -1.476395   -0.209688
2011-01-04  -0.554705   1.342504    0.245934    0.955521    NaN
2011-01-05  -0.351260   -0.798270   0.820535    -0.597322   0.546146
2011-01-06  0.132924    0.501027    -1.139487   1.107873    NaN

数据情况(见下文)似乎基本相同 - 将时间索引的值作为数据帧的子集连接到一系列中。但是它会出现标题中的ValueError错误(blah1 = (5, 286) blah2 = (5, 276))。为什么不起作用?

In[187]: df.head()
Out[188]:
high    low loc_h   loc_l
time                
2014-01-01 17:00:00 1.376235    1.375945    1.376235    1.375945
2014-01-01 17:01:00 1.376005    1.375775    NaN NaN
2014-01-01 17:02:00 1.375795    1.375445    NaN 1.375445
2014-01-01 17:03:00 1.375625    1.375515    NaN NaN
2014-01-01 17:04:00 1.375585    1.375585    NaN NaN
In [186]: df.index
Out[186]:
<class 'pandas.tseries.index.DatetimeIndex'>
[2014-01-01 17:00:00, ..., 2014-01-01 21:30:00]
Length: 271, Freq: None, Timezone: None

In [189]: hl.head()
Out[189]:
2014-01-01 17:00:00    1.376090
2014-01-01 17:02:00    1.375445
2014-01-01 17:05:00    1.376195
2014-01-01 17:10:00    1.375385
2014-01-01 17:12:00    1.376115
dtype: float64

In [187]:hl.index
Out[187]:
<class 'pandas.tseries.index.DatetimeIndex'>
[2014-01-01 17:00:00, ..., 2014-01-01 21:30:00]
Length: 89, Freq: None, Timezone: None

In: pd.concat([df, hl], axis=1)
Out: [stack trace] ValueError: Shape of passed values is (5, 286), indices imply (5, 276)

2
你试过使用append而不是concat吗?如果我正确理解了ValueError,它是在说有286行数据,但数据框的索引只期望276行。尝试检查len(df.index)len(h1.index) - alacy
df.append(hl) 出现 TypeError: 'NoneType' object is not iterable 错误。但是我尝试了 join - 谢谢! :) - birone
没问题。请确保将您的答案标记为正确,这样未来的SO用户如果遇到类似的问题就可以快速找到您的解决方案。 - alacy
当它让我这么做时,我会去做。 - birone
4
错误提示信息可以更加有帮助,比如可能会说“您可能有一些重复的索引”…… - wordsforthewise
8个回答

86

我遇到了类似的问题(join可行,但concat失败)。

检查df1s1中是否有重复的索引值(例如,df1.index.is_unique

删除重复的索引值(例如,df.drop_duplicates(inplace=True))或参考此处的其中一种方法 https://dev59.com/9Gcs5IYBdhLWcg3wOBRC#34297689 可以解决此问题。


4
谢谢,这样可以了!我是这样做的:df = pd.concat([df1, df2], axis=1, join_axes=[df1.index])。如果df2里有重复的索引,那么就会出现错误。这很有道理,因为它不知道如何映射两个数据框中重复的索引。 - sparrow
3
要删除重复的索引,请使用 df = df.loc[df.index.drop_duplicates()]。参考:https://pandas.pydata.org/pandas-docs/stable/generated/pandas.Index.drop_duplicates.html - BallpointBen
3
检查两个索引中是否存在重复的索引值,这个建议可能会帮助到阅读此问题的许多人。 - dsugasa
为了删除重复的索引,最好的方法是 df = df[~df.index.duplicated(keep='first')] 参见 https://dev59.com/9Gcs5IYBdhLWcg3wOBRC - ztl

43

我的问题是不同的索引,以下代码解决了我的问题。

df1.reset_index(drop=True, inplace=True)
df2.reset_index(drop=True, inplace=True)
df = pd.concat([df1, df2], axis=1)

1
我遇到了这个问题,但通过 reset_index() 方法解决了。原始索引的问题是什么?reset_index() 方法是如何解决的? - rubpa

7
要删除重复的索引,请使用 df = df.loc[df.index.drop_duplicates()]。参见pandas.pydata.org/pandas-docs/stable/generated/…。这种方法是错误的,因为df.index.drop_duplicates()返回一个唯一索引列表,但是当您使用这些唯一索引重新索引回数据框时,它仍会返回所有记录。这可能是因为使用其中一个重复的索引进行索引将返回索引的所有实例。相反,请使用df.index.duplicated(),它返回一个布尔列表(添加~以获取非重复记录)。
df = df.loc[~df.index.duplicated()]

5
Aus_lacy的帖子给了我尝试相关方法的想法,其中join确实有效:
In [196]:

hl.name = 'hl'
Out[196]:
'hl'
In [199]:

df.join(hl).head(4)
Out[199]:
high    low loc_h   loc_l   hl
2014-01-01 17:00:00 1.376235    1.375945    1.376235    1.375945    1.376090
2014-01-01 17:01:00 1.376005    1.375775    NaN NaN NaN
2014-01-01 17:02:00 1.375795    1.375445    NaN 1.375445    1.375445
2014-01-01 17:03:00 1.375625    1.375515    NaN NaN NaN

希望能够解释一下为什么concat在这个示例中起作用,但在另一个数据上却不起作用。


3
您的索引可能包含重复值。
import pandas as pd

T1_INDEX = [
    0,
    1,  # <= !!! if I write e.g.: "0" here then it fails
    0.2,
]
T1_COLUMNS = [
    'A', 'B', 'C', 'D'
]
T1 = [
    [1.0, 1.1, 1.2, 1.3],
    [2.0, 2.1, 2.2, 2.3],
    [3.0, 3.1, 3.2, 3.3],
]

T2_INDEX = [
    1.2,
    2.11,
]

T2_COLUMNS = [
    'D', 'E', 'F',
]
T2 = [
    [54.0, 5324.1, 3234.2],
    [55.0, 14.5324, 2324.2],
    # [3.0, 3.1, 3.2],
]
df1 = pd.DataFrame(T1, columns=T1_COLUMNS, index=T1_INDEX)
df2 = pd.DataFrame(T2, columns=T2_COLUMNS, index=T2_INDEX)


print(pd.concat([pd.DataFrame({})] + [df2, df1], axis=1))

1

尝试在连接索引后进行排序

result=pd.concat([df1,df2]).sort_index()

0
如果尝试在axis=0上进行连接,这个方法对我有效(将其转换为记录列表)。
df = pd.DataFrame(
    df1.to_dict('records') + \
    df2.to_dict('records')
)

-2

也许很简单,试试这个方法。如果你有一个DataFrame,请确保你要合并的两个矩阵或向量具有相同的行名称/索引。

我曾经遇到过同样的问题。我改变了行的名称索引,使它们相互匹配。下面是一个例子,一个矩阵(主成分)和一个向量(目标)具有相同的行索引(我在图片左侧用蓝色圈出来了)。

之前,“当它不起作用时”,我的矩阵具有正常的行索引(0、1、2、3),而我的向量具有行索引(ID0、ID1、ID2、ID3)。然后我将向量的行索引更改为(0、1、2、3),这对我有用。

在此输入图片描述


网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接