我从某个地方收到了一个DataFrame,并希望创建另一个具有相同数量和列和行(索引)名称的DataFrame。例如,假设原始数据框创建为
import pandas as pd
df1 = pd.DataFrame([[11,12],[21,22]], columns=['c1','c2'], index=['i1','i2'])
我通过显式定义列和名称来复制结构:
df2 = pd.DataFrame(columns=df1.columns, index=df1.index)
我不想复制数据,否则我只能写df2 = df1.copy()
。换句话说,在创建df2之后,它必须只包含NaN元素:
In [1]: df1
Out[1]:
c1 c2
i1 11 12
i2 21 22
In [2]: df2
Out[2]:
c1 c2
i1 NaN NaN
i2 NaN NaN
是否有更惯用的方法呢?
答案 0 :(得分:26)
在version 0.18 of pandas, the DataFrame constructor中没有选项来创建数据框,就像使用NaN而不是值来创建另一个数据框一样。
您使用的代码df2 = pd.DataFrame(columns=df1.columns, index=df1.index)
是最合乎逻辑的方式,改进它的唯一方法是拼出更多您正在做的是添加data=None
,以便其他编码人员直接看到你有意遗漏了你正在创建的新数据框中的数据。
TLDR:我的建议是:
df2 = pd.DataFrame(data=None, columns=df1.columns, index=df1.index)
非常像你的,但更多的拼写。
答案 1 :(得分:22)
这是reindex_like
的工作。从原文开始:
df1 = pd.DataFrame([[11, 12], [21, 22]], columns=['c1', 'c2'], index=['i1', 'i2'])
构造一个空的DataFrame并像df1:
一样重新索引它pd.DataFrame().reindex_like(df1)
Out:
c1 c2
i1 NaN NaN
i2 NaN NaN
答案 2 :(得分:10)
In [1]: import pandas as pd
In [2]: df = pd.DataFrame([[1, 'a'], [2, 'b'], [3, 'c']],
...: columns=['num', 'char'])
In [3]: df
Out[3]:
num char
0 1 a
1 2 b
2 3 c
In [4]: df.dtypes
Out[4]:
num int64
char object
dtype: object
DataFrame
的列进行简单的DataFrame
初始化,但不提供数据:In [5]: empty_copy_1 = pd.DataFrame(data=None, columns=df.columns)
In [6]: empty_copy_1
Out[6]:
Empty DataFrame
Columns: [num, char]
Index: []
In [7]: empty_copy_1.dtypes
Out[7]:
num object
char object
dtype: object
如您所见,列数据类型与原始DataFrame
中的列数据类型不同。
dtype
... 如果要保留列数据类型,则需要一次构建DataFrame
一个Series
In [8]: empty_copy_2 = pd.DataFrame.from_items([
...: (name, pd.Series(data=None, dtype=series.dtype))
...: for name, series in df.iteritems()])
In [9]: empty_copy_2
Out[9]:
Empty DataFrame
Columns: [num, char]
Index: []
In [10]: empty_copy_2.dtypes
Out[10]:
num int64
char object
dtype: object
答案 3 :(得分:6)
一个简单的替代方法 - 首先将原始数据框(df1)中数据类型的基本结构或索引和列复制到df2
df2 = df1.iloc[0:0]
然后用空行填充数据帧 - 需要调整伪代码以更好地匹配您的实际结构:
s = pd.Series([Nan,Nan,Nan], index=['Col1', 'Col2', 'Col3'])
遍历df1
中的行df2 = df2.append(s)
答案 4 :(得分:5)
我的案例是创建数据框架的副本,该副本没有数据也没有索引。通过执行以下操作可以实现这一目标。这将保持列的dtype。
empty_copy = df.drop(df.index)
答案 5 :(得分:2)
你只需mask
notna()
即
df1 = pd.DataFrame([[11, 12], [21, 22]], columns=['c1', 'c2'], index=['i1', 'i2'])
df2 = df1.mask(df1.notna())
c1 c2
i1 NaN NaN
i2 NaN NaN
答案 6 :(得分:0)
这在熊猫0.22中对我有用:
df2 = pd.DataFrame(index=df.index.delete(slice(None)), columns=df.columns)
转换类型:
df2 = df2.astype(df.dtypes)
delete(slice(None))
如果您不想保留索引的值。
答案 7 :(得分:0)
我知道这是一个老问题,但我想我会加两分钱。
def df_cols_like(df):
"""
Returns an empty data frame with the same column names and types as df
"""
df2 = pd.DataFrame({i[0]: pd.Series(dtype=i[1])
for i in df.dtypes.iteritems()},
columns=df.dtypes.index)
return df2
此方法围绕输入数据帧df.dtypes
的{{1}}属性,df
。 pd.Series
由空pd.DataFrame
对象的字典构成,这些对象使用输入列名命名,列顺序取自输入pd.Series
。
答案 8 :(得分:0)
将 df 结构复制到 df2 的简单方法是:
df2 = pd.DataFrame(columns=df.columns)