

本文属于机器翻译版本。若本译文内容与英语原文存在差异，则一律以英文原文为准。

# 数据质量


数据质量监控会自动监控生产中的机器学习 (ML) 模型，并在出现数据质量问题时向您发送通知。生产中的机器学习模型必须对实际数据进行预测，而这些数据并不像大多数训练数据集那样经过了精心策划。如果模型在生产过程中接收到的数据的统计性质偏离了训练所依据的基准数据的性质，则模型将开始失去其预测的准确性。Amazon SageMaker 模型监控器使用规则来检测数据偏差，并在出现偏差时提醒您。要监控数据质量，请执行以下步骤：
+ 启用数据捕获。这会捕获来自实时推理端点或批量转换作业的推理输入和输出，并将数据存储在 Amazon S3 中。有关更多信息，请参阅[数据采集](model-monitor-data-capture.md)。
+ 创建基准。在此步骤中，运行基准作业以分析您提供的输入数据集。该基准使用 [Deequ](https://github.com/awslabs/deequ)（一个基于 Apache Spark 构建的开源库，用于衡量大型数据集中的数据质量）计算每项特征的基准架构约束和统计数据。有关更多信息，请参阅[创建基准](model-monitor-create-baseline.md)。
+ 定义和计划数据质量监控作业。有关数据质量监控作业的具体信息和代码示例，请参阅[计划数据质量监控作业](model-monitor-schedule-data-monitor.md)。有关监控作业的一般信息，请参阅[计划监控作业](model-monitor-scheduling.md)。
  + （可选）使用预处理和后处理脚本来转换数据质量分析得出的数据。有关更多信息，请参阅 [预处理和后处理](model-monitor-pre-and-post-processing.md)。
+ 查看数据质量指标。有关更多信息，请参阅 [统计数据的架构（statistics.json 文件）](model-monitor-interpreting-statistics.md)。
+ 将数据质量监控与 Amazon 集成 CloudWatch。有关更多信息，请参阅 [CloudWatch 指标](model-monitor-interpreting-cloudwatch.md)。
+ 解释监控作业的结果。有关更多信息，请参阅 [解释结果](model-monitor-interpreting-results.md)。
+ 如果您使用的是实时端点，请使用 SageMaker Studio 启用数据质量监控并可视化结果。有关更多信息，请参阅 [在 Amazon SageMaker Studio 中可视化实时端点的结果](model-monitor-interpreting-visualize-results.md)。

**注意**  
Model Monitor 仅计算表格数据的模型指标和统计数据。例如，仍然可以监控将图像作为输入并根据该图像输出标签的图像分类模型。Model Monitor 将能够计算输出（而不是输入）的指标和统计数据。

**Topics**
+ [

# 创建基准
](model-monitor-create-baseline.md)
+ [

# 计划数据质量监控作业
](model-monitor-schedule-data-monitor.md)
+ [

# 统计数据的架构（statistics.json 文件）
](model-monitor-interpreting-statistics.md)
+ [

# CloudWatch 指标
](model-monitor-interpreting-cloudwatch.md)
+ [

# 违规情况的架构（constraint\$1violations.json 文件）
](model-monitor-interpreting-violations.md)

# 创建基准
创建基准

统计数据和约束的基准计算需作为检测数据漂移和其他数据质量问题的标准。Model Monitor 提供了一个内置容器，该容器能够自动建议针对 CSV 和平面 JSON 输入的约束。此*sagemaker-model-monitor-analyzer*容器还为您提供了一系列模型监控功能，包括根据基准进行约束验证和发出 Amazon CloudWatch 指标。此容器基于 Spark 版本 3.3.0，并通过 [Deequ](https://github.com/awslabs/deequ) 版本 2.0.2 构建。基准数据集中的所有列名称都必须符合 Spark。对于列名称，请仅使用小写字符，`_` 是唯一的特殊字符。

用来训练模型的训练数据集通常是一个很好的基准数据集。训练数据集数据架构和推理数据集架构应完全匹配（特征的数量和顺序）。请注意，假设这些 prediction/output 列是训练数据集中的第一列。在训练数据集中，您可以让 SageMaker AI 建议一组基线约束条件并生成描述性统计数据以探索数据。对于此示例，上传已用于训练本示例中包含的预训练模型的训练数据集。如果您已将训练数据集存储在 Amazon S3 中，则可以直接指向该数据集。

**从训练数据集创建基准** 

当您的训练数据准备就绪并存储在 Amazon S3 中时，请`DefaultModelMonitor.suggest_baseline(..)`使用 Amaz [ SageMaker on Python 软件开发工具包](https://sagemaker.readthedocs.io/en/stable)开始基准处理任务。这将使用 [Amazon SageMaker 模型监控器预建容器](model-monitor-pre-built-container.md)，它会生成基准统计数据，建议数据集的基准约束并将其写入您指定的 `output_s3_uri` 位置。

```
from sagemaker.model_monitor import DefaultModelMonitor
from sagemaker.model_monitor.dataset_format import DatasetFormat

my_default_monitor = DefaultModelMonitor(
    role=role,
    instance_count=1,
    instance_type='ml.m5.xlarge',
    volume_size_in_gb=20,
    max_runtime_in_seconds=3600,
)

my_default_monitor.suggest_baseline(
    baseline_dataset=baseline_data_uri+'/training-dataset-with-header.csv',
    dataset_format=DatasetFormat.csv(header=True),
    output_s3_uri=baseline_results_uri,
    wait=True
)
```

**注意**  
如果您将训练数据集中的 feature/column 名称作为第一行并设置`header=True`选项（如上一个代码示例所示）， SageMaker AI 将使用约束和统计文件中的要素名称。

数据集的基准统计数据包含在 statistics.json 文件中，建议的基准约束包含在 constraints.json 文件中，这两个文件位于您使用 `output_s3_uri` 指定的位置。

表格数据集统计数据和约束的输出文件


| 文件名称 | 说明 | 
| --- | --- | 
| statistics.json |  此文件应具有所分析数据集中每个特征的列式统计数据。有关此文件的架构的更多信息，请参阅[统计数据的架构（statistics.json 文件）](model-monitor-byoc-statistics.md)。  | 
| constraints.json |  此文件应对观察到的特征有约束。有关此文件的架构的更多信息，请参阅[约束的架构（constraints.json 文件）](model-monitor-byoc-constraints.md)。  | 

[Amaz SageMaker on Python 软件开发工具包](https://sagemaker.readthedocs.io/en/stable)提供了用于生成基准统计数据和约束条件的便捷函数。但是，如果您想改为直接调用处理作业来达到此目的，则需要设置 `Environment` 映射，如以下示例中所示：

```
"Environment": {
    "dataset_format": "{\"csv\”: { \”header\”: true}",
    "dataset_source": "/opt/ml/processing/sm_input",
    "output_path": "/opt/ml/processing/sm_output",
    "publish_cloudwatch_metrics": "Disabled",
}
```

# 计划数据质量监控作业
计划数据质量监控作业

创建基准后，您可以调用 `DefaultModelMonitor` 类实例的 `create_monitoring_schedule()` 方法来计划每小时一次的数据质量监控。以下几节介绍如何为部署到实时端点的模型以及为批量转换作业创建数据质量监控。

**重要**  
创建监控计划时，您可以指定批量转换输入或端点输入，但不能同时指定两者。

## 对部署到实时端点的模型进行数据质量监控


要为实时端点计划数据质量监控，请将 `EndpointInput` 实例传递给 `DefaultModelMonitor` 实例的 `endpoint_input` 参数，如以下代码示例所示：

```
from sagemaker.model_monitor import CronExpressionGenerator
                
data_quality_model_monitor = DefaultModelMonitor(
   role=sagemaker.get_execution_role(),
   ...
)

schedule = data_quality_model_monitor.create_monitoring_schedule(
   monitor_schedule_name=schedule_name,
   post_analytics_processor_script=s3_code_postprocessor_uri,
   output_s3_uri=s3_report_path,
   schedule_cron_expression=CronExpressionGenerator.hourly(),
   statistics=data_quality_model_monitor.baseline_statistics(),
   constraints=data_quality_model_monitor.suggested_constraints(),
   schedule_cron_expression=CronExpressionGenerator.hourly(),
   enable_cloudwatch_metrics=True,
   endpoint_input=EndpointInput(
        endpoint_name=endpoint_name,
        destination="/opt/ml/processing/input/endpoint",
   )
)
```

## 对批量转换作业进行数据质量监控


要为批量转换作业计划数据质量监控，请将 `BatchTransformInput` 实例传递给 `DefaultModelMonitor` 实例的 `batch_transform_input` 参数，如以下代码示例所示：

```
from sagemaker.model_monitor import CronExpressionGenerator
                
data_quality_model_monitor = DefaultModelMonitor(
   role=sagemaker.get_execution_role(),
   ...
)

schedule = data_quality_model_monitor.create_monitoring_schedule(
    monitor_schedule_name=mon_schedule_name,
    batch_transform_input=BatchTransformInput(
        data_captured_destination_s3_uri=s3_capture_upload_path,
        destination="/opt/ml/processing/input",
        dataset_format=MonitoringDatasetFormat.csv(header=False),
    ),
    output_s3_uri=s3_report_path,
    statistics= statistics_path,
    constraints = constraints_path,
    schedule_cron_expression=CronExpressionGenerator.hourly(),
    enable_cloudwatch_metrics=True,
)
```

# 统计数据的架构（statistics.json 文件）
统计信息

Amazon SageMaker 模型监控器预建容器根据统计数据进行计算。 column/feature 将为基准数据集以及正在分析的当前数据集计算统计数据。

```
{
    "version": 0,
    # dataset level stats
    "dataset": {
        "item_count": number
    },
    # feature level stats
    "features": [
        {
            "name": "feature-name",
            "inferred_type": "Fractional" | "Integral",
            "numerical_statistics": {
                "common": {
                    "num_present": number,
                    "num_missing": number
                },
                "mean": number,
                "sum": number,
                "std_dev": number,
                "min": number,
                "max": number,
                "distribution": {
                    "kll": {
                        "buckets": [
                            {
                                "lower_bound": number,
                                "upper_bound": number,
                                "count": number
                            }
                        ],
                        "sketch": {
                            "parameters": {
                                "c": number,
                                "k": number
                            },
                            "data": [
                                [
                                    num,
                                    num,
                                    num,
                                    num
                                ],
                                [
                                    num,
                                    num
                                ][
                                    num,
                                    num
                                ]
                            ]
                        }#sketch
                    }#KLL
                }#distribution
            }#num_stats
        },
        {
            "name": "feature-name",
            "inferred_type": "String",
            "string_statistics": {
                "common": {
                    "num_present": number,
                    "num_missing": number
                },
                "distinct_count": number,
                "distribution": {
                    "categorical": {
                         "buckets": [
                                {
                                    "value": "string",
                                    "count": number
                                }
                          ]
                     }
                }
            },
            #provision for custom stats
        }
    ]
}
```

注意以下几点：
+ 预构建的容器将计算 [KLL 草图](https://datasketches.apache.org/docs/KLL/KLLSketch.html)，这是一个紧凑的分位数草图。
+ 默认情况下，我们将分配具体化到 10 个存储桶中。目前，这是不可配置的。

# CloudWatch 指标
CloudWatch 指标

您可以使用内置的 Amazon SageMaker 模型监控器容器来获取 CloudWatch 指标。当该`emit_metrics`选项位于基准约束文件`Enabled`中时， SageMaker AI 会针对在以下命名空间的数据集中 feature/column 观察到的每个指标发出这些指标：
+ 带 `EndpointName` 和 `ScheduleName` 维度的 `For real-time endpoints: /aws/sagemaker/Endpoints/data-metric` 命名空间。
+ 带 `MonitoringSchedule` 维度的 `For batch transform jobs: /aws/sagemaker/ModelMonitoring/data-metric` 命名空间。

对于数值字段，内置容器会发出以下 CloudWatch指标：
+ 指标：最大值 → 查询 `MetricName: feature_data_{feature_name}, Stat: Max`
+ 指标：最小值 → 查询 `MetricName: feature_data_{feature_name}, Stat: Min`
+ 指标：和 → 查询 `MetricName: feature_data_{feature_name}, Stat: Sum`
+ 指标: SampleCount → 查询 `MetricName: feature_data_{feature_name}, Stat: SampleCount`
+ 指标：平均值 → 查询 `MetricName: feature_data_{feature_name}, Stat: Average`

对于数值和字符串字段，内置容器都会发出以下 CloudWatch 指标：
+ 指标：完整性 → 查询 `MetricName: feature_non_null_{feature_name}, Stat: Sum`
+ 指标：基准偏差 → 查询 `MetricName: feature_baseline_drift_{feature_name}, Stat: Sum`

# 违规情况的架构（constraint\$1violations.json 文件）
违规

违规情况文件作为 `MonitoringExecution` 的输出生成，其中列出了针对所分析的当前数据集评估约束（在 constraints.json 文件中指定）的结果。Amazon SageMaker 模型监控器预建容器提供以下违规检查。

```
{
    "violations": [{
      "feature_name" : "string",
      "constraint_check_type" :
              "data_type_check",
            | "completeness_check",
            | "baseline_drift_check",
            | "missing_column_check",
            | "extra_column_check",
            | "categorical_values_check"
      "description" : "string"
    }]
}
```

监控的违规情况的类型 


| 违规情况检查类型 | 说明  | 
| --- | --- | 
| data\$1type\$1check | 如果当前执行中的数据类型与基准数据集中的数据类型不同，则会标记此违规情况。 在基准步骤中，生成的约束会为每个列建议推断的数据类型。可以调整 `monitoring_config.datatype_check_threshold` 参数，以便调整标记为违规时的阈值。  | 
| completeness\$1check | 如果当前执行中观察到的完整性（非空项目的百分比）超过了为每个特征指定的完整性阈值中指定的阈值，则会标记此违规情况。 在基准步骤中，生成的约束会建议一个完整性值。  | 
| baseline\$1drift\$1check | 如果当前数据集和基准数据集之间计算的分布距离大于 `monitoring_config.comparison_threshold` 中指定的阈值，则会标记此违规情况。  | 
| missing\$1column\$1check | 如果当前数据集中的列数小于基准数据集中的列数，则会标记此违规情况。  | 
| extra\$1column\$1check | 如果当前数据集中的列数大于基准数据集中的列数，则会标记此违规情况。  | 
| categorical\$1values\$1check | 如果当前数据集中的未知值多于基准数据集中的未知值，则会标记此违规情况。此值由 `monitoring_config.domain_content_threshold` 中的阈值决定。  | 