掘金 人工智能 前天 08:53
Amazon Bedrock 上的模型擂台赛:Nova、Claude,谁是最强图片/视频审核大模型?
index_new5.html
../../../zaker_core/zaker_tpl_static/wap/tpl_guoji1.html

 

本文评估了亚马逊云科技Amazon Bedrock上多模态大模型在视频和图像内容审核方面的表现。通过对比Nova系列(Lite和Pro)与Anthropic的Claude 3.7 Sonnet模型,从准确率、误报率和漏报率等多维度分析,为构建基于大模型的内容审核方案提供参考。实验涵盖色情和暴力内容检测,并提供了详细的实验步骤和结果分析。

📊 Claude 3.7 Sonnet模型在图片内容审核中表现最佳,总体准确率达到97.22%,尤其在色情内容检测上表现突出,但对暴力内容的检测准确率相对较低。

🖼️ Nova Pro模型在视频内容检测上优于Nova Lite,总体性能更佳,误报率和漏报率均低于Nova Lite,表现出更强的平衡性,在各类内容检测上更均衡。

💰 Nova Lite模型价格最具竞争力,但准确率略低于其他模型。Nova Pro价格是Nova Lite的4倍,但总体准确率提升有限。Claude 3.7 Sonnet模型价格较高,但准确率提升显著。

⚙️ 实验基于Kaggle和GitHub公开数据集,测试了模型的色情和暴力内容检测能力,并提供了详细的实验步骤,包括数据预处理、Prompt设计和结果分析,方便用户复现和参考。

前言

本文将探讨如何使用亚马逊云科技上提供的生成式 AI 大模型进行视频以及图像内容审核。本文将使用相同的视频图像审核测试数据集,从审核准确率、误报率、漏报率等多项指标全面评估亚马逊云科技 Amazon Bedrock 上三款多模态大模型的表现差异,这包括亚马逊自研大模型 Nova 系列的 Lite 和 Pro 模型、Anthropic 的 Claude 3.7 Sonnet 模型,对比分析不同模型在色情内容和暴力内容审核场景下的优势,为您选择和构建合适的基于大模型的内容审核解决方案提供洞见与参考。如果您对文本内容审核感兴趣,请参阅 Amazon Bedrock 上的模型擂台赛:DeepSeek、Nova、Claude,谁是最强文本审核大模型?

此外,亚马逊云科技提供了一系列托管人工智能服务 Amazon RekognitionAmazon ComprehendAmazon TranscribeAmazon TranslateAmazon Bedrock 以及其他技术,来帮助您快速打造自动化智能化多模态内容审核方案(详情参考博客),包括图像、视频、文本和音频审核工作流程。

一、图片内容检测分析

数据集概况

本文分别测试了模型在色情内容以及暴力内容的多模态检测,使用的公开数据集来自 Kaggle 以及 github。两个数据集合并并抽取了 400 数据作为此次试验的总数据集。

测试 Prompt

所有测试均使用以下统一的 prompt 进行评估:

你是一个专业的图片内容审核专家,负责识别图片中的暴力和色情内容。请仔细分析图片内容并做出精确判断。请遵循以下分类标准:- Violent: 图片必须包含以下一项或多项:* 真实人物之间的打斗、殴打、攻击行为(注意:与表演、电影、体育竞技区分)* 明显的流血、伤口或身体伤害* 使用武器威胁或伤害他人* 明显的肢体冲突和人身伤害场景* 街头斗殴、帮派暴力或群体攻击行为* 体育场上发生斗殴事件- Non-violent: 不包含上述暴力元素的图片,即使是:* 竞技性体育运动(包括拳击、摔跤、格斗比赛等)* 表演或电影中的打斗场景* 游戏或动画中的非真实暴力* 人们进行日常活动(吃饭、行走、交谈、工作等)【色情内容精确定义】- Porn: 图片必须包含以下一项或多项:* 明确的性行为或性交场景* 裸露的生殖器官* 裸露的成人胸部(女性)* 明显的性行为暗示姿势或动作* 性器官特写或强调* 明确的性行为表演- Non-porn: 不包含上述色情元素的图片,即使是:* 穿着比基尼、泳装的人* 部分暴露但不完全裸露的内容* 健身、瑜伽或体育活动中的紧身服装* 具有性感元素但不露骨的内容* 艺术性质的裸体(如雕塑、古典艺术)分析步骤:1. 首先详细描述图片中看到的内容,包括人物、动作、环境和上下文2. 分别判断暴力和色情两个维度3. 给出最终分类结果,必须是以下四种之一:- "Violent"(有暴力,无色情)- "Non-violent"(无暴力,无色情)- "Porn"(有色情,无论是否有暴力)- "Non-porn"(无色情,可能包含性感元素但不露骨)如有任何不确定性,请倾向于将内容标记为"Violent"或"Porn"。你的回答必须包含上述四个标签之一,后面跟着简短的解释理由。"""

注:本文使用的提示词并非是最佳实践,实际使用需要根据不同的场景对提示词进行优化以提升模型表现。

模型性能对比

色情内容检测

主要发现

总体准确率对比:

敏感内容检测能力:

非敏感内容检测能力:

检测偏好:

二、视频内容检测对比

在视频内容检测方面,我们使用的测试视频数据如下:

我们对 Nova Lite 和 Nova Pro 模型进行了对比测试,结果如下:

总体准确率

Nova Lite 混淆矩阵:

Nova Pro 混淆矩阵:

总体性能:

检测偏好与平衡性:

误报与漏报:

Nova Pro 和 Nova Lite 是目前 Amazon Bedrock 平台上唯二支持视频格式作为输入的模型,两个模型在视频检测上表现更为平衡,没有明显的偏向性,两个模型在视频检测中的误报率和漏报率也相对接近。价格方面,Nova Lite 每一千次的调用价格仅为 Nova Pro 的 7.5%。

三、综合比较与适用场景

总体性能:

检测偏好与平衡性:

误报与漏报:

价格对比:

四、实验步骤

实验步骤与 Amazon Bedrock 上的模型擂台赛:DeepSeek、Nova、Claude,谁是最强文本审核大模型?一致,您可参考 Sagemaker Notebook 中的代码为如下内容,并将数据存入 S3 或存入 Sagemaker Notebook 环境中后,即可进行测试。

import boto3import pandas as pdimport jsonimport timefrom tqdm import tqdmimport concurrent.futuresimport osfrom botocore.exceptions import ClientErrorimport numpy as npimport base64from urllib.parse import urlparseimport iofrom PIL import Image# 定义CSV文件路径csv_file = 'combined_dataset_fixed.csv'# 读取包含图片路径的CSV文件df = pd.read_csv(csv_file)# 初始化Bedrock客户端bedrock_runtime = boto3.client(    service_name='bedrock-runtime',    region_name='us-east-1'  # 确保Claude模型在此区域可用)# 初始化S3客户端s3_client = boto3.client('s3', region_name='us-west-1')# 确保Bedrock有权限访问S3桶def check_s3_permissions():    try:        # 检查桶是否存在        s3_client.head_bucket(Bucket="video-moderation-dataset")        print("成功连接到S3桶 'video-moderation-dataset'")        return True    except Exception as e:        print(f"无法访问S3桶: {str(e)}")        # 如果只处理本地文件,可以继续        return True# 模型ID# model_id = 'us.anthropic.claude-3-7-sonnet-20250219-v1:0'model_id = 'us.amazon.nova-pro-v1:0'# model_id='us.amazon.nova-lite-v1:0'# 判断路径是S3路径还是本地路径def is_s3_path(path):    return path.startswith('s3://')# 从S3获取图片字节def get_image_from_s3(s3_uri):    try:        parsed_url = urlparse(s3_uri)        bucket_name = parsed_url.netloc        object_key = parsed_url.path.lstrip('/')                response = s3_client.get_object(Bucket=bucket_name, Key=object_key)        image_bytes = response['Body'].read()        return image_bytes    except Exception as e:        print(f"从S3获取图片失败: {str(e)}")        return None# 从本地文件系统获取图片字节def get_image_from_local(file_path):    try:        with open(file_path, 'rb') as f:            image_bytes = f.read()        return image_bytes    except Exception as e:        print(f"从本地文件系统获取图片失败: {str(e)}")        return None# 获取图片字节,无论是从S3还是本地def get_image_bytes(path):    if is_s3_path(path):        return get_image_from_s3(path)    else:        return get_image_from_local(path)# 处理图片,确保格式正确def process_image(image_bytes):    try:        # 使用PIL打开图片        image = Image.open(io.BytesIO(image_bytes))                # 转换为RGB模式(如果是RGBA或其他模式)        if image.mode != 'RGB':            image = image.convert('RGB')                # 调整大小,确保不超过API限制        max_size = 4096  # 根据API限制调整        if max(image.size) > max_size:            ratio = max_size / max(image.size)            new_size = (int(image.size[0] * ratio), int(image.size[1] * ratio))            image = image.resize(new_size, Image.LANCZOS)                # 转换为JPEG格式的字节        buffer = io.BytesIO()        image.save(buffer, format="JPEG", quality=85)        processed_bytes = buffer.getvalue()                return processed_bytes    except Exception as e:        print(f"处理图片时出错: {str(e)}")        return image_bytes  # 如果处理失败,返回原始字节# 分析单个图片def analyze_image(image_path, label):    print(f"处理图片: {image_path}")    try:        # 获取图片字节        image_bytes = get_image_bytes(image_path)        if image_bytes is None:            return {                'image_path': image_path,                'label': label,                'nova_lite_result': 'error',                'nova_lite_response': '无法获取图片数据'            }                # 处理图片,确保格式正确        processed_image = process_image(image_bytes)                # 获取图片扩展名        image_ext = "jpeg"  # 默认为jpeg,因为我们在process_image中转换为JPEG                # prompt = """你是一个专业的图片内容审核专家,负责识别图片中的暴力和色情内容。请仔细分析图片内容并做出精确判断。        #             请遵循以下分类标准:        #             【暴力内容定义】        #             - Violent: 图片包含真实的肢体冲突、打斗、斗殴、攻击行为,特别是街头打架、武器威胁、流血场景、明显的身体伤害或任何形式的人身伤害。        #             - Non-violent: 图片展示和平的人类活动,如体育运动(即使是竞技性的)、日常生活场景(吃饭、行走、交谈)、工作场景等,没有真实的暴力冲突。        #             【色情内容定义】        #             - Porn: 图片包含露骨的性行为、生殖器官暴露、性交行为、明确的性意图活动、裸体(非艺术性质)、性挑逗姿势等明确色情内容。        #             - Non-porn: 图片可能包含比基尼、泳装、部分暴露但不露骨的内容,虽可能具有性感元素,但不展示明确的性行为或完全裸露。        #             分析步骤:        #             1. 首先详细描述图片中看到的内容,包括人物、动作、环境和上下文        #             2. 分别判断暴力和色情两个维度        #             3. 给出最终分类结果,必须是以下四种之一:        #             - "Violent"(有暴力,无色情)        #             - "Non-violent"(无暴力,无色情)        #             - "Porn"(有色情,无论是否有暴力)        #             - "Non-porn"(无色情,可能包含性感元素但不露骨)        #             如有任何不确定性,请倾向于将内容标记为"Violent"或"Porn"。你的回答必须包含上述四个标签之一,后面跟着简短的解释理由。"""        prompt = """你是一个专业的图片内容审核专家,负责识别图片中的暴力和色情内容。请仔细分析图片内容并做出精确判断。                    请遵循以下分类标准:                    - Violent: 图片必须包含以下一项或多项:                    * 真实人物之间的打斗、殴打、攻击行为(注意:与表演、电影、体育竞技区分)                    * 明显的流血、伤口或身体伤害                    * 使用武器威胁或伤害他人                    * 明显的肢体冲突和人身伤害场景                    * 街头斗殴、帮派暴力或群体攻击行为                    * 体育场上发生斗殴事件                    - Non-violent: 不包含上述暴力元素的图片,即使是:                    * 竞技性体育运动(包括拳击、摔跤、格斗比赛等)                    * 表演或电影中的打斗场景                    * 游戏或动画中的非真实暴力                    * 人们进行日常活动(吃饭、行走、交谈、工作等)                    【色情内容精确定义】                    - Porn: 图片必须包含以下一项或多项:                    * 明确的性行为或性交场景                    * 裸露的生殖器官                    * 裸露的成人胸部(女性)                    * 明显的性行为暗示姿势或动作                    * 性器官特写或强调                    * 明确的性行为表演                    - Non-porn: 不包含上述色情元素的图片,即使是:                    * 穿着比基尼、泳装的人                    * 部分暴露但不完全裸露的内容                    * 健身、瑜伽或体育活动中的紧身服装                    * 具有性感元素但不露骨的内容                    * 艺术性质的裸体(如雕塑、古典艺术)                    分析步骤:                    1. 首先详细描述图片中看到的内容,包括人物、动作、环境和上下文                    2. 分别判断暴力和色情两个维度                    3. 给出最终分类结果,必须是以下四种之一:                    - "Violent"(有暴力,无色情)                    - "Non-violent"(无暴力,无色情)                    - "Porn"(有色情,无论是否有暴力)                    - "Non-porn"(无色情,可能包含性感元素但不露骨)                    如有任何不确定性,请倾向于将内容标记为"Violent"或"Porn"。你的回答必须包含上述四个标签之一,后面跟着简短的解释理由。"""        max_retries = 2        retry_count = 0        response = None  # 初始化response变量                # 打印图片路径和大小信息进行调试        print(f"图片路径: {image_path}")        print(f"处理后图片大小: {len(processed_image)} 字节")                # 调用Bedrock Converse API,直接传入图片字节        while retry_count < max_retries:            try:                response = bedrock_runtime.converse(                    modelId=model_id,                    messages=[                        {                            'role': 'user',                            'content': [                                {                                    'text': prompt                                },                                {                                    'image': {                                        'format': image_ext,                                        'source': {                                            'bytes': processed_image                                        }                                    }                                }                            ]                        }                    ]                )                break            except Exception as e:                retry_count += 1                if retry_count >= max_retries:                    print(f"调用模型失败,已达到最大重试次数 ({max_retries})。错误: {str(e)}")                    raise e                else:                    print(f"调用模型失败,正在进行第 {retry_count} 次重试。错误: {str(e)}")                    sleep_time = 30                    time.sleep(sleep_time)                # 检查response是否为None        if response is None:            return {                'image_path': image_path,                'label': label,                'nova_lite_result': 'error',                'nova_lite_response': '无法获取模型响应'            }                        # 解析响应        try:            response_text = response['output']['message']['content'][0]['text']        except KeyError:            try:                response_text = response['messages'][0]['content'][0]['text']            except KeyError:                response_text = "无法从响应中提取文本"                # 根据标签类型提取判断结果        if label in ['violent', 'non-violent']:            # 提取判断结果(violent或non-violent)            if 'violent' in response_text.lower() and not 'non-violent' in response_text.lower():                result = 'violent'            elif 'non-violent' in response_text.lower():                result = 'non-violent'            else:                # 如果无法明确判断,则进一步分析响应                if any(word in response_text.lower() for word in ['fight', 'attack', 'violence', 'aggressive', 'harm', 'push', 'hit', 'slap', 'touch', 'contact', 'fall', 'strike', 'throw', 'conflict', 'swing', 'wave', 'stick', 'bat']):                    result = 'violent'                else:                    result = 'non-violent'                elif label in ['porn', 'non-porn']:            # 提取判断结果(porn或non-porn)            if 'porn' in response_text.lower() and not 'non-porn' in response_text.lower():                result = 'porn'            elif 'non-porn' in response_text.lower():                result = 'non-porn'            else:                # 如果无法明确判断,则进一步分析响应                if any(word in response_text.lower() for word in ['nude', 'naked', 'sexual', 'explicit', 'adult', 'inappropriate']):                    result = 'porn'                else:                    result = 'non-porn'        else:            # 默认情况,直接使用标签作为结果            result = label                # 添加一些延迟以避免API限制        time.sleep(0.5)                return {            'image_path': image_path,            'label': label,            'nova_lite_result': result,            'nova_lite_response': response_text        }        except Exception as e:        print(f"处理图片 {image_path} 时出错: {str(e)}")        return {            'image_path': image_path,            'label': label,            'nova_lite_result': 'error',            'nova_lite_response': str(e)        }# 主函数def main():    # 检查S3权限    if not check_s3_permissions():        print("请确保已正确配置S3桶权限")        return            # 创建结果列表    results = []        # 获取图片路径和标签    image_data = list(zip(df['image_path'], df['label']))        print(f"开始分析 {len(image_data)} 个图片 ...")        # 使用线程池并行处理图片(限制并发数以避免API限制)    with concurrent.futures.ThreadPoolExecutor(max_workers=1) as executor:        futures = []        for image_path, label in image_data:            future = executor.submit(analyze_image, image_path, label)            futures.append(future)                # 使用tqdm显示进度        for future in tqdm(concurrent.futures.as_completed(futures), total=len(futures), desc="分析图片"):            result = future.result()            if result:                results.append(result)        # 创建结果DataFrame    results_df = pd.DataFrame(results)    successful_results = results_df[results_df['nova_lite_result'] != 'error']        # 保存结果到新的CSV文件    results_df.to_csv('image_analysis_results_nova.csv', index=False)        print(f"总共处理 {len(results_df)} 个图片,成功 {len(successful_results)} 个,失败 {len(results_df) - len(successful_results)} 个")        # 计算准确率    accuracy = (successful_results['label'] == successful_results['nova_lite_result']).mean()    print(f"Bedrock模型分析完成。准确率: {accuracy:.2%}")        # 打印混淆矩阵    print("\n混淆矩阵:")    confusion = pd.crosstab(        successful_results['label'],         successful_results['nova_lite_result'],         rownames=['实际'],         colnames=['预测']    )    print(confusion)if __name__ == "__main__":    main()

清理资源

最后,请及时清理资源,避免造成不必要的费用。若您使用了 Sagemaker Notebook 运行实验及测试,并将数据存储在了 S3 存储桶中,可通过删除创建的 S3 存储桶以及中止 SageMaker Notebook 来完成资源的清理。

总结

您可以根据自身业务需求、对漏报/误报的容忍度以及预算情况,选择最适合的模型进行内容审核工作。在实际应用中,可能需要结合多种模型或技术,构建更加全面和有效的内容审核系统。希望通过以上分析,可以为您带来内容审核上的一些洞见。

*前述特定亚马逊云科技生成式人工智能相关的服务仅在亚马逊云科技海外区域可用,亚马逊云科技中国仅为帮助您了解行业前沿技术和发展海外业务选择推介该服务。

本篇作者

本期最新实验《多模一站通 —— Amazon Bedrock 上的基础模型初体验

✨ 精心设计,旨在引导您深入探索Amazon Bedrock的模型选择与调用、模型自动化评估以及安全围栏(Guardrail)等重要功能。无需管理基础设施,利用亚马逊技术与生态,快速集成与部署生成式AI模型能力。

⏩️[点击进入实验] 即刻开启 AI 开发之旅

构建无限, 探索启程!

Fish AI Reader

Fish AI Reader

AI辅助创作,多种专业模板,深度分析,高质量内容生成。从观点提取到深度思考,FishAI为您提供全方位的创作支持。新版本引入自定义参数,让您的创作更加个性化和精准。

FishAI

FishAI

鱼阅,AI 时代的下一个智能信息助手,助你摆脱信息焦虑

联系邮箱 441953276@qq.com

相关标签

亚马逊云科技 大模型 内容审核 图像识别 视频识别
相关文章