是,polynomialfeatures默认自动补全低阶项和常数项;degree=2时必含1、x₁、x₂、x₁²、x₁x₂、x₂²,仅通过include_bias=false和interaction_only=true可分别剔除常数项与幂次项。

PolynomialFeatures 会自动补全低阶项吗?
会,而且默认就补。只要设置 degree=2,PolynomialFeatures 不仅生成所有二阶交互项(如 x1*x2),还会保留所有一阶项(x1, x2)和常数项(1)。这不是可选项,是硬编码行为。
如果你只想保留交互项、不要低阶项,必须显式关掉:
- 设 include_bias=False 去掉常数项
- 设 interaction_only=True 禁用幂次项(如 x1**2),只留不同特征间的乘积
例如,输入两列 [a, b],degree=2, interaction_only=True, include_bias=False 输出只有 [a*b];不设 interaction_only 则输出 [a, b, a*b](include_bias=False 下)。
fit_transform 和 transform 的调用顺序不能颠倒
这是最常踩的坑:在训练集上调用 fit_transform 后,对测试集必须只调用 transform,不能再次 fit_transform。
原因在于 PolynomialFeatures 虽然没“参数学习”过程,但 fit 阶段会记录原始特征数量(n_features_in_)和列名映射关系。如果对测试集重新 fit_transform,它会按测试集维度重建特征空间,导致训练/测试特征维度不一致,后续模型直接报错 ValueError: X has 5 features, but PolynomialFeatures is expecting 3 features。
正确流程只有这一种:
- poly = PolynomialFeatures(degree=2)
- X_train_poly = poly.fit_transform(X_train)
- X_test_poly = poly.transform(X_test)
高维稀疏矩阵下 PolynomialFeatures 性能断崖式下降
当原始特征数超过 10–15 列且 degree >= 2 时,输出特征数爆炸增长。比如 20 列 + degree=3 → 最多产生约 1770 列(含所有组合),内存占用和计算时间都会飙升。
应对策略:
- 先用 interaction_only=True 限制为纯两两交互,避免立方项
- 对高基数类别特征,先做独热编码再传给 PolynomialFeatures,否则它会对编码后的 0/1 列也做乘法,徒增大量无意义的零值列
- 如果原始数据是稀疏矩阵(如 scipy.sparse.csr_matrix),PolynomialFeatures 默认会转成稠密数组,瞬间吃光内存。必须手动设 order="F" 并配合 np.array(..., order="F") 预处理,或改用 sklearn.preprocessing.PolynomialFeatures(include_bias=False).fit_transform(sparse_matrix.toarray())(仅适用于小规模稀疏矩阵)
与 Pipeline 配合时要注意 feature_names_in_ 的丢失
从 scikit-learn 1.2 开始,PolynomialFeatures 支持 get_feature_names_out(),但前提是它得知道原始列名。如果上游是 pd.DataFrame,直接传进去没问题;但如果上游是 numpy.ndarray 或经过了其他 transformer(如 StandardScaler),feature_names_in_ 就会丢失,调用 get_feature_names_out() 会报 AttributeError: 'PolynomialFeatures' object has no attribute 'feature_names_in_'。
解决办法:
- 在 pipeline 最前端用 FunctionTransformer(lambda x: x, validate=False) 包一层,并手动设 feature_names_in_
- 更稳妥的是:单独用 PolynomialFeatures 处理 X,用 get_feature_names_out(input_features=original_columns) 显式传入原始列名
- 或者干脆放弃自动命名,用列索引定位关键交互项(比如你知道第 12 列是 age*income),毕竟实际建模中解释性常让位于稳定性
交互特征不是加得越多越好,PolynomialFeatures 的输出列名不带业务含义,容易掩盖真实变量关系。上线前务必检查是否引入了强共线性(比如 height 和 height**2),并用 np.linalg.cond 或方差膨胀因子(VIF)验证——这点比怎么调参重要得多。
Python免费学习笔记(深入):立即使用
在学习笔记中,你将探索 Python 的核心概念和高级技巧!











