我正在使用 pandera 开发 Pandas DataFrame Schema 验证代码(在 Python 中),并且正在寻找验证 DataFrame 对列组合具有唯一值的最佳方法。
原始数据由他人提供,为CSV格式。我的代码将 CSV 加载到 Pandas DataFrame 中,然后执行 pandera DataFrameSchema 验证数据框具有使用 X 和 Y 坐标的地理坐标系列。 数据的本质是数据集中的每一行都应该有一个唯一的 X,Y 坐标。
csv 文件的一般形式:
x_coord、y_coord、value_A、value_B
12.1234、23.2345、27.23、32.84
34.3456、45.4567、21.12、22.32
....
....
使用 pandera,我能想到的唯一方法是:
采取多步骤的方法:
这种方法似乎有点笨拙,我正在寻找其他可以更多利用 pandera 灵活性的选项。
实现上面的代码是:
import pandas as pd
import pandera as pa
def get_valid_coord_df(filename):
df = pd.read_csv(filename)
schema = DataFrameSchema(columns={
'x_coord': pa.Column(pa.Float,
Check.in_range(0, 100_000)),
'y_coord': pa.Column(pa.Float,
Check.in_range(0, 100_000)),
'value_A': pa.Column(pa.Float,
Check.in_range(0, 20)),
'value_B': pa.Column(pa.Float,
Check.in_range(0, 20))
},
strict=True, ordered=True)
schema.validate(df, lazy=True) #will raise SchemaError
df_coord = pd.DataFrame(df['x_coord'].astype(str) + ',' + df['x_coord'].astype(str))
schema_coord = DataFrameSchema(columns={
'x_coord': pa.Column(pa.String,
allow_duplicates=False)})
schema_coord.validate(df_coord, lazy=True) #will raise SchemaError
return df
答案 0 :(得分:2)
在这里,您可以使用 wide checks 访问 Check
函数 arg 中的整个数据帧:
import pandera as pa
schema = pa.DataFrameSchema(
columns={
"x_coord": pa.Column(pa.Float, pa.Check.in_range(0, 100_000)),
"y_coord": pa.Column(pa.Float, pa.Check.in_range(0, 100_000)),
"value_A": pa.Column(pa.Float, pa.Check.in_range(0, 20)),
"value_B": pa.Column(pa.Float, pa.Check.in_range(0, 20)),
},
# checks at the DataFrameSchema level take the dataframe as input
# (as opposed to the series at the Column level)
checks=pa.Check(lambda df: ~df[["x_coord", "y_coord"]].duplicated()),
strict=True,
ordered=True,
)
如果您发现自己在代码库中更频繁地使用此检查,您还可以定义一个 check extension,以便您可以在 pa.Check
命名空间中访问它:
import pandera.extensions as extensions
@extensions.register_check_method(
statistics=["columns"], supported_types=pd.DataFrame,
)
def unique_columns(pandas_obj, *, columns):
return ~pandas_obj[columns].duplicated()
schema = pa.DataFrameSchema(
checks=pa.Check.unique_columns(["x_coord", "y_coord"])
)
schema.validate(
pd.DataFrame(
{
"x_coord": [1.0, 2.0, 3.0],
"y_coord": [4.0, 5.0, 6.0],
}
)
)