簡體   English   中英

將 sklearn.svm.SVR model 保存為 JSON 而不是酸洗

[英]Saving an sklearn.svm.SVR model as JSON instead of pickling

我有一個訓練有素的 SVR model 需要以JSON格式保存,而不是酸洗。

JSONifying 訓練后的 model 背后的想法是簡單地捕獲權重和其他“擬合”屬性的 state。 然后,我可以稍后設置這些屬性來進行預測。 這是我做的一個實現:

    # assume SVR has been trained
    regressor = SVR()
    regressor.fit(x_train, y_train)

    # saving the regressor params in a JSON file for later retrieval
    with open(f'saved_regressor_params.json', 'w', encoding='utf-8') as outfile:
        json.dump(regressor.get_params(), outfile)

    # finding the fitted attributes of SVR()
    # if an attribute is trailed by '_', it's a fitted attribute
    attrs = [i for i in dir(regressor) if i.endswith('_') and not i.endswith('__')]
    remove_list = ['coef_', '_repr_html_', '_repr_mimebundle_'] # unnecessary attributes
    
    for attr in remove_list:
        if attr in attrs:
            attrs.remove(attr)


    # deserialize NumPy arrays and save trained attribute values into JSON file
    attr_dict = {i: getattr(regressor, i) for i in attrs}

    for k in attr_dict:
        if isinstance(attr_dict[k], np.ndarray):
            attr_dict[k] = attr_dict[k].tolist()

    # dump JSON for prediction
    with open(f'saved_regressor_{index}.json', 'w', encoding='utf-8') as outfile:    
        json.dump(attr_dict, 
                    outfile, 
                    separators=(',', ':'), 
                    sort_keys=True, 
                    indent=4)

這將創建兩個單獨json文件。 一個名為saved_regressor_params.json的文件保存了 SVR 所需的某些參數,另一個名為saved_regressor.json將屬性及其訓練值存儲為對象。 示例(saved_regressor.json):

{
    "_dual_coef_":[
        [
            -1.0,
            -1.0,
            -1.0,
        ]
    ],
    "_intercept_":[
        1.323423423
    ],
         ...
         ...

    "_n_support_":[
        3
    ]
}

稍后,我可以創建一個新的 SVR() model 並通過從我們剛剛創建的現有 JSON 文件中調用它們來簡單地將這些參數和屬性設置到其中。 然后,調用predict()方法進行預測。 像這樣(在一個新文件中):

predict_svr = SVR()

#load the json from the files
obj_text = codecs.open('saved_regressor_params.json', 'r', encoding='utf-8').read()
params = json.loads(obj_text)

obj_text = codecs.open('saved_regressor.json', 'r', encoding='utf-8').read()
attributes = json.loads(obj_text)

#setting params
predict_svr.set_params(**params)

# setting attributes
for k in attributes:
        if isinstance(attributes[k], list):
            setattr(predict_svr, k, np.array(attributes[k]))
        else:
            setattr(predict_svr, k, attributes[k])
        
predict_svr.predict(...)

但是,在此過程中,由於某種原因,無法設置名為: n_support_的特定屬性。 即使我忽略n_support_屬性,它也會產生額外的錯誤。 (我的邏輯是錯誤的還是我在這里遺漏了什么?)

因此,我正在尋找不同的方法或巧妙的方法將 SVR model 保存到 JSON 中。

我已經嘗試過現有的第三方幫助庫,例如: sklearn_json 這些庫傾向於完美地導出線性模型,而不是支持向量。

根據文檔(版本 1.1.2),在 OP 中缺少可重現的示例

from sklearn.svm import SVR
from sklearn.pipeline import make_pipeline
from sklearn.preprocessing import StandardScaler
import numpy as np
n_samples, n_features = 10, 5
rng = np.random.RandomState(0)
y = rng.randn(n_samples)
X = rng.randn(n_samples, n_features)
regressor = SVR(C=1.0, epsilon=0.2)
regressor.fit(X, y)

然后是 JSON 序列化/反序列化的草圖

import json
# serialize
serialized = json.dumps({
    k: v.tolist() if isinstance(v, np.ndarray) else v 
    for k, v in regressor.__dict__.items()
})

# deserialize
regressor2 = SVR()
regressor2.__dict__ = {
     k: np.asarray(v) if isinstance(v, list) else v 
     for k, v in json.loads(serialized).items()
}

# test
assert np.all(regressor.predict(X) == regressor2.predict(X))

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM