gpt4 book ai didi

python - 如何构建可以处理非数字目标的用户友好的 sklearn 回归器?

转载 作者:行者123 更新时间:2023-12-03 20:25:50 27 4
gpt4 key购买 nike

目标

我正在尝试构建封装过程的回归器

  • 将目标从非数字格式转换为数字格式
  • 在内部,所有计算都使用数字
  • 在将数值呈现给用户之前将其逆变换回原始格式。

  • 理想情况下,最终用户应该能够在不了解目标转换内部结构的情况下使用回归器。开发人员应提供实现变换和逆变换逻辑的函数。

    原型(prototype)演示

    sklearn.compose.TransformedTargetRegressor 的帮助下我能够建立一个线性回归模型,该模型接受时间戳作为目标,并在内部将它们转换为自 1970-01-01 00:00:00(Unix 纪元)以来演变的秒数。 fitpredict方法已经按预期工作。
    import pandas as pd
    from sklearn.compose import TransformedTargetRegressor
    from sklearn.linear_model import LinearRegression
    from sklearn.preprocessing import FunctionTransformer

    _check_inverse = False

    # helper to convert a 2D numpy array of timestamps to a 2D array of seconds
    def _to_float(timestamps):
    deltas = pd.DataFrame(timestamps).sub(pd.Timestamp(0))
    return deltas.apply(lambda s: s.dt.total_seconds()).values

    # helper to convert a 2D numpy array of seconds to a 2D array of timestamps
    def _to_timestamp(seconds):
    return pd.DataFrame(seconds).apply(pd.to_datetime, unit='s').values

    # build transformer from helper functions
    time_transformer = FunctionTransformer(
    func=_to_float,
    inverse_func=_to_timestamp,
    validate=True,
    check_inverse=_check_inverse
    )

    # build TransformedTargetRegressor
    tt_reg = TransformedTargetRegressor(
    regressor=LinearRegression(),
    transformer=time_transformer,
    check_inverse=_check_inverse
    )

    用法:
    >>> import numpy as np
    >>> X = np.array([[1], [2], [3]], dtype=float)
    >>> y = pd.date_range(start=0, periods=3, freq='min')
    >>> tt_reg = tt_reg.fit(X, y)
    >>> tt_reg.predict(X)
    array(['1970-01-01T00:00:00.000000000', '1970-01-01T00:01:00.000000000',
    '1970-01-01T00:02:00.000000000'], dtype='datetime64[ns]')

    但是,使用 predict 结果的方法内部如 score (以及可能更复杂的 sklearn 回归器的其他方法)失败,因为它们无法处理 _to_timestamp 的输出:
    >>> tt_reg.score(X, y)
    Traceback (most recent call last):
    File "<input>", line 1, in <module>
    File "C:\Users\actualpanda\.virtualenvs\SomeProject--3333Ox_\lib\site-packages\sklearn\base.py", line 435, in score
    return r2_score(y, y_pred, sample_weight=sample_weight,
    File "C:\Users\actualpanda\.virtualenvs\SomeProject--3333Ox_\lib\site-packages\sklearn\metrics\_regression.py", line 591, in r2_score
    numerator = (weight * (y_true - y_pred) ** 2).sum(axis=0,
    TypeError: ufunc 'square' not supported for the input types, and the inputs could not be safely coerced to any supported types according to the casting rule ''safe''

    为了得到分数,用户必须知道 tt_reg.regressor_ 的内部结构。 .
    >>> tt_reg.regressor_.score(X, y.to_series().sub(pd.Timestamp(0)).dt.total_seconds())
    1.0

    问题

    是否有一种可行的方法来构建强大的、用户友好的 sklearn 回归器,可以处理非数字目标并且不会泄露它们的内部?

    最佳答案

    更新score如评论中所述,方法可能会解决您的问题。

    from sklearn.utils import check_array


    class MyTransformedTargetRegressor(TransformedTargetRegressor):

    def score(self, X, y):
    y = check_array(y, accept_sparse=False, force_all_finite=True,
    ensure_2d=False)
    if y.ndim == 1:
    y_2d = y.reshape(-1, 1)
    else:
    y_2d = y
    y_trans = self.transformer_.transform(y_2d)

    if y_trans.ndim == 2 and y_trans.shape[1] == 1:
    y_trans = y_trans.squeeze(axis=1)

    return self.regressor_.score(X, y_trans)

    让我们尝试使用不同的回归器

    from sklearn.ensemble import BaggingRegressor
    tt_reg = MyTransformedTargetRegressor(
    regressor=BaggingRegressor(),
    transformer=time_transformer,
    check_inverse=_check_inverse
    )


    import numpy as np
    n_samples =10000
    X = np.arange(n_samples).reshape(-1,1)
    y = pd.date_range(start=0, periods=n_samples, freq='min')
    tt_reg = tt_reg.fit(X, y)
    tt_reg.predict(X)
    print(tt_reg.score(X, y))

    # 0.9999999891236799

    关于python - 如何构建可以处理非数字目标的用户友好的 sklearn 回归器?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/61403912/

    27 4 0
    Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
    广告合作:1813099741@qq.com 6ren.com