AWS SageMaker培训脚本:如何传递自定义用户参数

时间:2020-01-08 15:40:29

标签: python scikit-learn amazon-sagemaker

我正在使用Scikit-learn和SageMaker Python SDK训练分类器。
整个过程包括三个连续的阶段:

  1. 使用训练和验证数据集的超参数调整作业
  2. 在1.中建立具有最佳超参数的
  3. 培训工作,并且 整个数据集(从1开始的培训+验证)
  4. 使用2中提供的“预适应”模型和用于校准的其他数据集来训练已校准的模型。

我需要拆分流程的原因是要保存在步骤2中创建的未经校准的模型。

对于每个步骤,我都准备了一个训练脚本,具体说明如下:https://sagemaker.readthedocs.io/en/stable/using_sklearn.html#prepare-a-scikit-learn-training-script

这三个脚本非常相似,为避免代码冗余,我想在这三种情况下使用带有附加逻辑的单个脚本。更准确地说,我想将其他自定义参数传递给.fitsagemaker.tuner.HyperparameterTuner对象的sagemaker.sklearn.estimator.SKLearn方法,以便能够根据用法来操作脚本中的逻辑(阶段1.,2。或3.)。

我已经尝试过入侵SM_CHANNEL_XXX
parser.add_argument('--myparam', type=str, default=os.environ.get('SM_CHANNEL_MYPRAM')) 调用.fit(inputs={'train': ..., 'test': ..., 'myparam': myvalue})时,但它需要一个有效的s3 URI。

关于如何将额外的自定义参数传递到训练脚本的任何想法?

1 个答案:

答案 0 :(得分:0)

您可以在创建估算器之前,不通过fit方法传递超参数,而直接传递给step。文档中的示例为:

sklearn_estimator = SKLearn('sklearn-train.py',
                        train_instance_type='ml.m4.xlarge',
                        framework_version='0.20.0',
                        hyperparameters = {'epochs': 20, 'batch-size': 64, 'learning- 
rate': 0.1})
sklearn_estimator.fit({'train': 's3://my-data-bucket/path/to/my/training/data',
                    'test': 's3://my-data-bucket/path/to/my/test/data'})

这是将参数(从笔记本电脑)引入训练脚本以通过parser.add_argument访问的方式。如果只有一个脚本,则可以在脚本中处理逻辑。 但这不会在sagemaker.tuner.HyperparameterTuner的.fit方法中添加自定义参数。

我按以下顺序优化脚本中的参数,然后应用最佳参数(也仅使用一个训练脚本)。也许您将此应用到您的案例中。您应该能够在脚本中使用joblib.dump保存中间模型:

param_grid = [{'vect__ngram_range': [(1, 1)],
           'vect__stop_words': [stop, None],
           'clf__penalty': ['l1', 'l2'],
           'clf__C': [1.0, 10.0, 100.0]},
          {'vect__ngram_range': [(1, 1)],
           'vect__stop_words': [stop, None],
           'vect__use_idf':[False],
           'vect__norm':[None],
           'clf__penalty': ['l1', 'l2'],
           'clf__C': [1.0, 10.0, 100.0]},
          ]

lr_tfidf = Pipeline([('vect', tfidf),
                 ('clf', LogisticRegression(random_state=0))])

gs_lr_tfidf = GridSearchCV(lr_tfidf, param_grid,
                       scoring='accuracy',
                       cv=5,
                       verbose=1,
                       n_jobs=-1)


gs_lr_tfidf.fit(X_train, y_train)