# 营销文案生成 **Repository Path**: tide_trend/marketing-doc-generation ## Basic Information - **Project Name**: 营销文案生成 - **Description**: 使用电商数据自动抽取营销文案 - **Primary Language**: Python - **License**: Apache-2.0 - **Default Branch**: master - **Homepage**: None - **GVP Project**: No ## Statistics - **Stars**: 1 - **Forks**: 2 - **Created**: 2021-08-01 - **Last Updated**: 2024-01-12 ## Categories & Tags **Categories**: Uncategorized **Tags**: None ## README ## 智能营销项目 ### 目录 ### 1.项目介绍 ### 2.数据说明 ### 3.开发环境 ### 4.文件结构 ### 5.模型说明 *** ### 1.项目介绍 本项目为京东NLP高阶实战训练营二期的第二个项目。 ``` (1)项目内容:利用京东商城商品的说明信息(标题、属性标签和OCR)生成相应的营销文案。 (2)使用模型:seq2seq、attention、pointer networks (3)项目目的:掌握seq2seq+attention的基本制作方法与套路,掌握pointer networks的搭建方 法,掌握评估指标如Rouge、BLEU的计算逻辑,掌握Beam Search的搜索逻辑 ``` ### 2.数据说明 ``` (1)数据为Json格式,内容是每件商品的编号、标题(title)、属性标签(kb)、ocr信息及参考文案(reference); (2)模型的输入为标题(title)、属性标签(kb)、ocr信息; (3)参考文案(reference)作为ground truth; ``` ``` { "20": { "title": "奢侈品 皮带 男 鳄鱼皮 评价 黑色 鳄鱼皮", "kb": { "材质": "鳄鱼皮", "包装": "礼盒", "带扣": "平滑扣/板扣", "风格": "商务休闲", "适用人群": "中年", }, "ocr": "商城搜索,整皮裁剪,匠心手工制作,细腻的钢扣头,电镀钢扣头,定制优质五金,优质牛皮背面,辅料标准,内部定型层,质感油亮,骨刺饱满,产品展示,钢扣头,产品细,黑色,臊鱼皮选,高档耐磨,头层牛皮,扣头材质,中间夹层的优质材料...", "reference": "男鳄鱼皮真皮腰带优先选用骨刺丰满立体的鳄鱼皮制作,内部使用优质皮糠纸作为中间夹层,是各种高奢皮带的中间夹层的优质材料。背面侧面采用牛皮包边,皮质柔软,质感舒适,更有档次。" }, "21": { "title": "凯乐石 男女 款 攀岩 弹力 快干 长裤 秋冬 版 男 藏蓝 修身 版型", "kb": { "尺码": "XXL", "功能": "耐磨", "适用人群": "男士", "裤长": "长裤" }, "ocr": "颜色展示,产品展示,男女款攀岩弹力快干长裤9a,商品档案,臀部、膝盖立体有型,外挂挂环,男款裤脚口左右暗扣调节设计,可折叠固定裤脚,透气斜式插手袋,立体剪裁技术,修身合体版型,女款同样裤脚口左右暗扣调节设计...", "reference": "选取抗撕式混合型织物用作裤身的打造主材,直面户外尖锐小物的刮蹭,耐磨不易划破,裤头的后幅位置采用松紧设计,动态服帖着腰身,并添加了织物挂环,可用于悬挂攀岩装备,便于户外运动穿着。" }, } ``` ### 3.开发环境 Python环境:本地anaconda-python3.6.10, (注:因为需要使用pycharm开发,且本地GPU资源够使用,未在京东云平台部署) 主要依赖包: ``` torch==1.5.1 gensim==3.8.3 jieba==0.42.1 numpy==1.19.0 pandas==1.0.5 ``` ### 4.文件结构 ``` │ README.md │ ├─configs # 配置文件位置 │ │ settings.py # 配置信息 │ │ __init__.py │ ├─processed_data # 处理后的数据集 │ ├─saved_models # 模型存档 │ │ │ │ │ └─torch # 神经网络模型存档 │ │ │ └─checkpoints │ │ │ └─attn # 带有attention机制的网络 │ │ │ └─cov # 添加coverage机制的网络 │ │ │ └─ptn # ptn网络 │ ├─site_packages # 工具库 │ │ __init__.py │ │ │ ├─ml_libs # 机器学习工具库 │ │ │ __init__.py │ │ │ │ │ ├─nlp # 自然语言处理工具库 │ │ │ │ baidu.py # 百度翻译模块 │ │ │ │ base.py # 基础组件(如字典) │ │ │ │ sampling.py # EDA数据增强和tfidf-embedding词替换 │ │ │ │ metrics.py # 模型评估指标(本次为Rouge) │ │ │ │ settings.py # nlp工具库配置文件 │ │ │ │ stopwords.py # 停用词处理 │ │ │ │ __init__.py │ │ │ │ │ │ │ ├─data # 停用词数据集 │ │ │ │ └─stopwords-master │ │ │ │ baidu_stopwords.txt │ │ │ │ cn_stopwords.txt │ │ │ │ hit_stopwords.txt │ │ │ │ punctuation.txt │ │ │ │ README.md │ │ │ │ scu_stopwords.txt │ │ │ │ symbols.txt │ │ │ ├─utils # 通用工具库 │ │ │ dataframe.py # DataFrame操作 │ │ │ decorators.py # 装饰器 │ │ │ job.py # 数据、模型读取与存储 │ │ │ math.py # 数学工具 │ │ │ unzip.py # 解压工具 │ │ │ __init__.py │ ├─src # 模型相关文件 │ │ augmentation.py # 数据增强 │ │ datasets.py # 数据集读取 │ │ evalution.py # 模型评估 │ │ features.py # 特征抽取 │ │ models.py # 模型定义 │ │ preprocess.py # 数据清洗 │ │ train.py # 训练过程 │ │ __init__.py ``` ### 5.模型说明 最大特点:自己实现,纯手敲。自已结合课程、网上教程和原理解读的文章等,逐步探索、纠错,逐步实现encoder、decoder、seq2seq、 attention、BeamSearch、Rouge评估等内容,最后组装成为目前的基线模型。 第一次作业:搭建seq2seq + attention的基线模型 > + GRU内核:本次采用GRU作为encoder和decoder的内核,然后将两者联合起来整合成为seq2seq模型; > + seq2seq模型:在训练过程中直接调用seq2seq2模型,而不是分别训练encoder和decoder,简化了训练过程代码; > + attention采用Luong论文中的定义,分别实现了其中的dot、general和concat的实现方法; > + 特征提取部分,因为encoder中使用pack_padded_sequence需要输入是排过序的。为了提升GPU利用效率,提前将数据集按批次排序好,而不是在模型训练过程中排序; > + 词嵌入:采用gensim提前训练好词嵌入保存使用,而不是用nn.Embedding层。这样可以提升GPU利用效率,并且因为embedding固定,模型训练结果更加稳定; 下图为30个epoch,loss的下降情况 ![avatar](records/images/epoch30.png) 第二次作业:搭建pointer network + coverage基线模型 在第一次作业的基础上,对整体代码进行改动。可以在settings.py设置MODEL_CONF字典中的pointer为True,以执行ptn网络,也可以设置is_coverage为True,添加coverage; 第一次作业采用的batch_size=64,本次ptn网络采用的batch_size=32,可以从图中观察到batch_size=32的损失曲线,抖动更大一些。 loss: 2.0754 ![avatar](records/images/ptn网络.png) 第三次作业:对模型进行优化 (1)添加weight_tying:共享encoder embedding层权重矩阵、decoder embedding层权重矩阵,并将decoder中softmax前的线性变换,用embedding权重矩阵乘法代替 由于encoder和decoder使用gensim的embedding,等价于进行了权重共享,线性变换的weight_tying设置如下: ```python if weight_tying: Z = concat_output.mm(embedding_matrix_t) else: Z = self.out(concat_output) ``` (2)添加scheduled_sampling: > 添加一个reduce_teacher_forcing的方法,逐步降低学习率。 > 在decoder中,每一个时间步会都会按照teacher_forcing_rate进行采样 train.py ```python def reduce_teacher_forcing(): TRAIN_CONF['teacher_forcing'] *= TRAIN_CONF['teacher_forcing_decay_factor'] setattr(seq2seq.teacher_forcing, TRAIN_CONF['teacher_forcing']) ``` models.py ```python def renew_decoder_inputs(self, decoder_output, targets=None): output_as_inputs = True if self.use_teacher_forcing: if random() <= self.teacher_forcing: # decoder_inputs: (batch_size,) decoder_inputs = targets output_as_inputs = False if output_as_inputs: # max_ids: (batch_size, 1, 1) probs, max_ids = decoder_output.topk(1, dim=2) # decoder_inputs: (batch_size,) decoder_inputs = max_ids.squeeze() return decoder_inputs ``` (3)添加数据增强,包括tfidf-embedding词替换、回译和自助式样本生成 > 完结撒花