- 参考链接:进化策略及其在深度学习中的应用
General——深刻认识URL
你真的认识URL了吗?
URL中的#
字符
#
在URL中与服务器无关,也就是说正常访问服务器的URL不包含#
#
仅仅与本地浏览器对网页的定位相关#
由于不影响对远程服务器的访问,自然也不会存在于软件包的下载连接中
URL的正则表达式
参考博客:https://blog.csdn.net/qq_25384945/article/details/81219075
Python
1
http[s]?://(?:[a-zA-Z]|[0-9]|[$-_@.&+]|[!*\(\),]|(?:%[0-9a-fA-F][0-9a-fA-F]))+
JavaScript
1
/((([A-Za-z]{3,9}:(?:\/\/)?)(?:[\-;:&=\+\$,\w]+@)?[A-Za-z0-9\.\-]+|(?:www\.|[\-;:&=\+\$,\w]+@)[A-Za-z0-9\.\-]+)((?:\/[\+~%\/\.\w\-_]*)?\??(?:[\-\+=&;%@\.\w_]*)#?(?:[\.\!\/\\\w]*))?)/
Java
1
^(https?|ftp|file)://[-a-zA-Z0-9+&@#/%?=~_|!:,.;]*[-a-zA-Z0-9+&@#/%=~_|]
Python
DL——多任务学习权重优化
loss归一化
不确定权重
- Paper: https://openaccess.thecvf.com/content_cvpr_2018/papers/Kendall_Multi-Task_Learning_Using_CVPR_2018_paper.pdf
- https://zhuanlan.zhihu.com/p/425672909
- https://zhuanlan.zhihu.com/p/65137250
- https://blog.csdn.net/cv_family_z/article/details/78749992
- https://mp.weixin.qq.com/s/BOGhU2jMqD82EMkTHGMnuw
- 回归问题误差:正太分布,分类问题误差:玻尔兹曼分布(https://www.zhihu.com/question/274174763/answer/672202523)
Centos——挖矿病毒kdevtmpfsi查杀经历
挖矿病毒kdevtmpfsi查杀经历
问题简介
- 服务器: 阿里云主机服务器
- 系统: Centos7
- 表现: kdevtmpfsi进程占用400%(8核心处理器)CPU
- 时间: 2020-01-07报警, 2020-01-08处理
查杀经过
使用
clamscan
命令搜索所有文件, clamav详情见我之前的博客clamav安装与杀毒1
nohup clamscan / -r --infected -l clamscan.log > clamscan.out &
- 这一步比较花时间
查看扫描结果
1
cat clamscan.log | grep FOUND
/var/lib/docker/overlay/bdd049c71596d743907224a8dd6fdb3fb4ca76e3af8dfd6eee2d034de2be45a1/merged/tmp/kdevtmpfsi: Multios.Coinminer.Miner-6781728-2 FOUND
/var/lib/docker/overlay/bdd049c71596d743907224a8dd6fdb3fb4ca76e3af8dfd6eee2d034de2be45a1/merged/tmp/red2.so: Unix.Trojan.Gafgyt-6981174-0 FOUND
/var/lib/docker/overlay/bdd049c71596d743907224a8dd6fdb3fb4ca76e3af8dfd6eee2d034de2be45a1/upper/tmp/kdevtmpfsi: Multios.Coinminer.Miner-6781728-2 FOUND
/var/lib/docker/overlay/bdd049c71596d743907224a8dd6fdb3fb4ca76e3af8dfd6eee2d034de2be45a1/upper/tmp/red2.so: Unix.Trojan.Gafgyt-6981174-0 FOUND
删除这四个文件,这里直接到相关目录下查看发现
../tmp
目录下往往都是病毒文件(与kinsing
相关,全部删除)top
查看CPU信息确定挖矿进程kdevtmpfsi的进程号[pid]确定启动信息中启动命令,并删除(在这里查到的信息是文件已经被删除了)
1
ls /proc/[pid] -ali
查找父进程进程号
1
systemctl status [pid]
● docker-be9fcab033e6158f8ff7d6ac07d28cfd918375178c27e016aa800cbeef985161.scope - libcontainer container be9fcab033e6158f8ff7d6ac07d28cfd918375178c27e016aa800cbeef985161
Loaded: loaded (/run/systemd/system/docker-be9fcab033e6158f8ff7d6ac07d28cfd918375178c27e016aa800cbeef985161.scope; static; vendor preset: disabled)
Drop-In: /run/systemd/system/docker-be9fcab033e6158f8ff7d6ac07d28cfd918375178c27e016aa800cbeef985161.scope.d
└─50-BlockIOAccounting.conf, 50-CPUAccounting.conf, 50-DefaultDependencies.conf, 50-Delegate.conf, 50-Description.conf, 50-MemoryAccounting.conf, 50-Slice.conf
Active: active (running) since Mon 2019-11-11 11:24:17 UTC; 1 months 27 days ago
Tasks: 38
Memory: 2.3G
CGroup: /system.slice/docker-be9fcab033e6158f8ff7d6ac07d28cfd918375178c27e016aa800cbeef985161.scope
├─ 4475 redis-server *:6379
├─ 8528 sh -c /tmp/.ICEd-unix/vJhOU
├─ 8529 /tmp/.ICEd-unix/vJhOU
└─22822 /tmp/kdevtmpfsi
Warning: Journal has been rotated since unit was started. Log output is incomplete or unavailable.
杀死不需要的相关进程,如上面的
4475
,8528
,8529
,22822
查看是否还有需要杀死的进程,如果有,则杀死该进程
1
ps -ef | grep kinsing
top
确定挖矿进程已经被杀死
总结
- 查杀病毒两个小时未发现服务器有明显异常
- 第二天出现了,需要进一步查看,重启机器后问题没有再出现
CA——BCB出价推导
本文主要记录BCB出价的推导
- 其他参考链接:智能出价——BCB求解
BCB介绍
- 预算约束的出价,Budget Constrained Bidding(简称BCB),广告主的出价目标是设置一定预算,拿到最多的流量(点击或者订单)
问题定义
- 一般BCB优化问题的定义:
$$
\begin{align}
\max_{x_{ij}} \sum^N_{i=1} x_{ij} v_{ij} \\
s.t. \sum^N_{i=1} x_{ij} c_{ij} \le B \\
\sum^M_{j=1} x_{ij} = 1 \\
x_{ij} \in {0, 1}
\end{align}
$$
解法一
可以解得,最终结果为(求解过程参见RL-MPCA论文):
$$ j^* = \arg\max_{j} (v_{ij} - \lambda c_{ij}) $$
解法二
- 如果只有一个广告位置,且使用二价计费,原始问题可化简为
$$
\begin{align}
\max_{x_{i}} \sum^N_{i=1} x_{i} v_{i} \\
s.t. \sum^N_{i=1} x_{i} c_{i} \le B \\
x_{i} \in {0, 1}
\end{align}
$$
- 最终可解得结果为(求解参考链接:智能出价——BCB求解):
$$ bid = v_i / \lambda $$
关于两种解法的结果分析
- 本质上,两种解法结果应该是完全相同的,第一种解法中,如果只有一个广告位置,且使用二价计费,求解到的结果本质于第二种解法结果一致。
- 当 \(v_{i} > \lambda \cdot Price_{win} \)时(\(Price_{win} = c_{i}\),表示净胜价格), 此时选择\(bid > Price_{win}\)的出价即可获得本次竞拍,此时不管是解法一(取\(v_{ij} - \lambda * c_{ij}\) 最大的动作)还是解法二(\(bid=v_i/\lambda\))都会选择执行竞拍动作。
- 反之,当当\(v_{i} < \lambda \cdot Price_{win}\)时, 此时选择\(bid < Price_{win}\)的出价即可获得本次竞拍,此时不管是解法一还是解法二都会选择执行不竞拍动作。
- 解法一适用于任何场景,解法二则仅适用于只有一个广告位置,且使用二价计费的场景
- 解法二的结果使用起来会更简单:
- 解法一需要预估不同出价下的收益,实际上,在只有一个广告位置,且使用二价计费的场景,不竞争当前广告位置的价值为0,计费为0,若竞争,则价值为\(v_i\),计费为\(c_i\),所以仅需要预估价值\(v_i\),计费\(c_i\)。
- 解法二则可直接预估一个值\(v_i\)即可,不需要预估\(c_i\),即在线不需要预估净胜价格
- 但是离线流量回放求解\(\lambda\)时,理论上也需要预估一个净胜价格,或者在给出一个价格时,需要知道是否会竞争成功。\(c_i\)已经隐含在求解到的\(\lambda\)中
- 若对于任意竞拍,都给定净胜价格,那么解法一和解法二等价,都只需要预估\(v_i\)一个值即可
CA——WideAndDeep
背景
- 一般来说,模型最重要的是 Memorization 和 Generalization
- Memorization: 可以不精确地定义为学习 items 或者特征的频繁共现,并且从历史数据里面开发(exploiting)
- Generalization: 基于相关性的传递性(transitivity of correlation), 探索发现一些新的特征组合(从我出现或很少出现的组合)
Wide
- 注重记忆能力
- 手动特征交叉组合(实现低阶的特征组合)
Deep
- 泛化能力
- 高阶特征
- 低维稠密embedding
Wide and Deep
- 结合了Wide和Deep两个模型
- 不是模型的集成(Ensemble),这里称为联合训练(Joint Training)
- 集成的两个模型是分开独立训练的,然后预测的时候合并了两个模型的预测
- 联合训练是两个模型同时训练,训练时是加权相加的,每次训练时损失是一起传递
CA——多任务学习总结
多任务学习,multi-task learning
多任务学习的结构
ESMM及扩展
MMoE及相关变体
多任务学习的损失函数权重设置
基于人工经验的人工优化
- 一般思想是对齐损失函数均值,并按照业务偏好有所倾斜,如果愿意花时间尝试,往往能拿到不错的结果
基于贝叶斯推论的权重优化
- 基于不确定性的权重设置方法(Uncertainty Weighting)
- 基本公式
$$
L(\mathbf{W}, \sigma_1, \sigma_2,…,\sigma_K) = \sum_{k=1}^K \frac{1}{2\sigma^2}L(\mathbf{W}) + \log \sigma^2
$$- 上述公式可通过推导得出Multi-Task Learning Using Uncertainty to Weigh Losses for Scene Geometry and Semantics
- 可以推导,无论是回归问题还是分类问题(也可以是分类和回归问题的混合),都可以按照上面的方法设置损失函数(分类问题证明中会使用到一个近似值,不是严格推导)
- 推导是在假设
- \(\sigma\)是可学习的参数,初始设置固定值,然后使用梯度更新学习即可
- 使用简单,实际使用时效果也确实不错,建议人工调参也可以在先使用该方案拿到权重量级后继续
- 上述公式可通过推导得出Multi-Task Learning Using Uncertainty to Weigh Losses for Scene Geometry and Semantics
帕累托最优权重优化
内积的含义:向量A到向量B的投影长度与向量B长度的乘积
Algorithm1展示的是,对于两个任务的情况,图示展示了二维向量的情况,可以通过判断向量之间的关系确定求解\(\alpha\)的方式
- Algorithm2中的FrankWolfeSlover算法则是对Algorithm1的多任务扩展
其他参考,阿里巴巴多任务学习帕累托最优论文:A Pareto-Efficient Algorithm for Multiple Objective Optimization in E-Commerce Recommendation
损失函数优化
损失函数归一化
可用于解决由于不同任务损失函数量级差异带来的问题
普通版本
$$
L_{norm} = \frac{L_k(\mathbf{W})}{L_0(\mathbf{W_0})}
$$
- 使用各个任务自己的第一次输出的损失函数作为基础损失函数,其中\(L_0(\mathbf{W_0}\)为第一次计算loss的到的损失函数
滑动平均版本
$$
L_{base} = \alpha L_{base} + (1-\alpha) L_k \\
L_{norm} = \frac{L_k(\mathbf{W})}{L_{base}} \\
$$
- 使用滑动平均来记录基础损失函数,该方案可进一步减少由于初始化损失误差过大带来的问题
梯度归一化(GradNorm)
- 原始论文:GradNorm: Gradient Normalization for Adaptive Loss Balancing in Deep Multitask Networks
- 核心思想是对各任务的损失函数进行加权(\(w_i\))求和得到更新共享参数的损失函数
- “GradNorm”这个名字的由来是因为权重\(w_i\)是与梯度2范数的期望等有关的?
- 公式中\(w_i\)是各个任务损失函数对共享参数损失函数的权重,该权重初始值为1,在训练过程中逐步更新,每一步最后都保持该权重加和为\(T\)(\(T\)为任务数量,即保证权重均值为1)
- 问题:文中没有明确各个任务各自的参数如何更新,猜测各自更新即可
最佳实践
- 一般情况下,根据业务特点,尽量使用类似于ESMM结构
- 权重设置尝试次序:
- 对损失函数进行归一化(梯度归一化好像效果一般?)
- 权重设置时,先使用不确定性权重(Uncertainty Weighting)跑一版,得到基线
- 在Uncertainty Weighting的基础上,人工可以根据业务需要微调,可以偏向于需要的任务
- 帕累托最优实现复杂,且不一定有收益
- 复杂体现在:需要在每个batch上重新求解最优化问题,得到当前的loss权重(用上一个batch的梯度求解这一个batch的最优权重)
CA——Google-Ad-Click-Prediction
- 参考文献:Google KDD 2013,Ad Click Prediction: a View from the Trenches(引用量500+)
- 介绍了截止到2013年之前的点击率预估常用算法,FTRL是Google三年的结晶(2010-2013)
- 在线学习优化算法的发展历程:SGD->TG->FOBOS->RDA->FTRL-Proximal
核心贡献
- 基于传统的逻辑回归算法(Regularized Logistic Regression,正则化的逻辑回归)在点击率预估时的不足,提出一种在线逻辑回归算法,FTRL(Follow The Regularized Leader)
- per-coordinate learning rate
一些模型的比较和介绍
- 传统逻辑回归算法中使用OGD(Online Gradient Descent)是非常高效的,使用很小的计算资源就能得到较好的精确度.
- 但是OGD在生成稀疏模型方面表现不好(OGD + L1)
- 其他在稀疏性方面表现良好的方法有FOBOS, 截断梯度(Truncated Gradient)和 RDA(Regularized Dual Averaging)
- RDA在精确度和稀疏性方面做tradeoff, 效果好于FOBOS
- FTRL-Proximal号称可以同时获得RDA的稀疏性和OGD的精确度
- RDA模型是微软提出的一种在线优化算法,与OGD完全不同,能得到更加稀疏的模型,但是精确度不如OGD
FTRL-Proximal Learning (Online Learning And Sparsity)
- 也是通过L1正则化控制模型的稀疏度
推导过程
FTL(Follow The Leader)的介绍
OGD的更新方式
- 更新规则:
$$
\begin{align}
\mathbf{w}_{t+1} &= \mathbf{w}_t-\eta_t\mathbf{g}_t
\end{align}
$$
FTLR(Follow The Regularized Leader)
加上正则项的FTL
- 更新规则:
$$
\begin{align}
\mathbf{w}_{t+1} &= \arg\min_{\mathbf{w}}\left ( \mathbf{g}_{1:t}\cdot \mathbf{w} + \frac{1}{2}\sum_{s=1}^t \sigma_s || \mathbf{w} - \mathbf{w}_s||_2^2 + \lambda_1||\mathbf{w}||_1 \right ) \\
\mathbf{g}_{1:t} &= \sum_{i=1}^t\mathbf{g}_i
\end{align}
$$- 第一项是对损失函数梯度的贡献的一个估计
- 第二项是控制参数\(\mathbf{w}\)在每次迭代中变化不要太大
- 第三项是L1正则化,用于使模型变得稀疏(除了L1正则化项以外,也可以再加上L2正则化)
- 去掉正则化项就是FTL(Follow The Leader)
- \(\sigma_s\)是学习速率
- 这个学习速率可以用Per-Coordinate Learning Rate:
$$
\begin{align}
\eta_{t, i} &= \frac{\alpha}{\beta + \sqrt{\sum_{s=1}^t g_{s,i}^2}} \\
\mathbf{g}_s &= \nabla l_s(\mathbf{w})
\end{align}
$$
Per-Coordinate Learning Rates
- 对参数的每一维度分开训练,每个维度有自己的学习率
- 某个特征出现的次数越多,说明当前该特征对应的参数值越可信,学习率就应该越小
- 考虑了数据在每个特征上的分布不均匀性
- 参数某个维度上的样本数越少,这些样本就会得到越大的利用(具体表现就是该特征的学习率会比较大)
一个思考
- 问题:为什么机器学习中的学习率都是越来越小?
- 答案:因为刚开始训练时,参数的值不太可信(也就是说最终参数与当前参数的置信度比较低),所以更新时应该更新的步骤大一些,让当前的参数变化大一些,训练到后来,随着参数的值越来越可信(当前参数的置信度比较高),更新的步骤就应该小一些,让当前的变化小一些
一些工程上的Trick
Saving Memory at Massive Scale
Probabilistic Feature Inclusion
- 在高维数据中,大量的特征是出现频率非常低的(rare),半数的唯一特征甚至只出现一次
- 统计这些特征的代价是非常昂贵的,有些特征可能永远不会被实际使用(这里如何理解昂贵?也就是说训练了也没用?)
- 额外的读写数据是昂贵的,如果能丢弃一部分出现评论特别低的特征(比如出现频率低于k次)
- 实现稀疏可以使用L1正则化,也可以使用Probabilistic Feature Inclusion
- 关于Probabilistic Feature Inclusion的做法
- 当一个特征第一次出现时,以一定的概率接受这个新特征
- 效果作用于数据预处理阶段,但是可以在在线执行中设置
Possion Inclusion
- 对于新的特征,以概率p添加入模型
- 对于已经存在模型中的特征,正常更新其系数
Bloom Filter Inclusion
- 用布隆过滤器仅仅保留出现次数在n次以上的特征
Encoding Values with Fewer Bits
- 常用的OGD使用32或者64位浮点数编码来存储模型的系数
- Google提出可以使用16位浮点数来存储系数,同时加上一些策略
- 实验结果:将64位的浮点值换为为系数存储节省了75%的RAM内存空间(这还用实验?直接计算就得到了啊)
Training Many Similar Models
- 同时训练多个模型是超参数选择常用的方法
- 将可以共享的东西共享
- 在节省内存的同时,还可以节约网络带宽(存储一份Per-coordinate学习率,节省内存和带宽等),CPU(用同一个hash表检索特征,节省CPU)和硬盘空间
A Single Value Structure
- 有时候我们希望评估大量的模型在只有少量的特征组(groups of features)添加或者删除时的变化
- 对于每一维度(coordinate),仅仅存储一个系数值而不是多个(正常应该为每个模型存储一个)
- 存储该维度对应特征组的模型共享该系数
- 对每个特征,训练时每个模型都会计算自己的值,然后所有模型的取平均作为所有包含该维度特征模型的共享
Computing Learning Rates with Counts
- 对于每个特征来说,梯度和以及梯度平方和是必须计算的
- 梯度的计算必须准确,但是计算学习率却是可以粗糙计算的
- 仅仅统计样本出现次数(Counts)就能大概计算学习率
推导
- 假设包含一个给定特征的所有事件(events)具有有相同的概率(一般来说,这个近似是不可能的,但是在这个目标里面是可行的)
- 如何理解这个假设的意义呢?对于具有某个特征的所有样本,其取值为(正负例)是的概率是相等的,正例(click)概率都为\(p\)
- 进一步假设模型已经精确地学习到了概率
- 如果有分别有\(P,N\)个正负样本(events),则有\(p=\frac{P}{N+P}\)
- 则有对于逻辑回归(\(p(1-p)\))来说,正例的梯度为\(p-1\),负例的梯度为\(p\)
$$
\begin{align}
\sum g_{t,i}^2 &= \sum_{positive \ events}(1-p_t)^2 + \sum_{negative \ events}p_t^2 \\
&\approx P(1-\frac{P}{N+P})^2 + N(\frac{P}{N+P})^2 \\
&= \frac{PN}{N+P}
\end{align}
$$ - 也就是说,为了近似计算\(\sum g_{t,i}^2\),我们仅需要记录\(P,N\)即可
Subsampling Traning Data
- 典型的CTRs是远远低于50%,数据偏差很大,正例(点击)的样本很稀疏
- 在模型训练中正例样本相对而言更有价值
- 使用下采样:很大程度上降低数据量,同时保证对精度最小程度的影响
采样方法:
- 保留所有至少被点击过一次的请求(Query,也就是样本)
- 以一定比例\(r\in(0, 1]\)采样没有被点击过的请求
- 因为包含通用的特征(Feature Phase)计算,所以这种方法是合理的,但是需要纠偏(直接用采样后的样本训练会造成预测偏差)
- 加入一个重要性权重\(w_t\)
- \(w_t = 1\) for clicked queries
- \(w_t = \frac{1}{r}\) for queries with no clicks
- 本质上可以理解为这里是将采样时造成的负例比例偏差补齐
模型性能评估
Progressive Validation
- Progressive验证又称为在线损失(online loss)
- 与交叉验证(cross-validation)或留出法(hold out)验证是不同的
- 在服务查询中,在线损失能很好的代表我们的精度,因为在训练模型前,它仅仅在最新数据上评估其性能(因为这准确的模拟了当模型进行服务查询时发生了什么)
- 由于用了100%的数据作为训练和测试,在线损失比留出法验证有更好的统计数据
- 绝对指标往往会带来误导
- 即使预测是完美的,对数损失和其他指标的差异也依赖着问题的困难程度
- 不同的国家,不同请求的点击率不同(同为对数损失的最佳实践,50%的点击率会好于2%的点击率)
- 所以使用相对变化,看指标相对于base line改变了多少
- 从经验来看,相对指标在整个时间段内都很稳定
- 相同的指标计算应该对应在完全相同的数据(比如不同时段的损失比较是没有意义的)
置信度评估(Confidence Estimates)
- 对很多应用来说,除了评估广告的CTR,还要量化预测的期望精确度(the expected accuracy of the prediction)
校正预测(Calibrating Predictions)
- 系统偏差(Systematic Bias)指平均预测CTR(Average Predicted CTR)和观测CTR(Observed CTR)的差异
- 造成系统偏差的原因包括:
- 不精确的模型假设
- 学习算法的缺陷
- 在训练或者服务(预测)时不可用的隐藏特征
- 解决方案:
- 添加一个校正层将预测CTRs与观测CTR做匹配(match predicted CTRSs to observed click-through rates)
- 暂时不能提供有效的保证,保证校正影响的有效
- 校正的本质是找到(拟合)一个函数映射\(g\),使得模型输出值与真实概率值一一对应
- 逻辑回归中的sigmoid函数可以看做是一个校正预测的函数吗?
- 更多参考
一些说明
- 概率模型的搭建过程中,由于抽样与正则化等原因,导致模型的输出概率值明显偏离真实概率值
- [待更新:为什么抽样和正则化会影响模型的输出概率发生变化?]
- 此时的模型输出概率值仅仅有排序的意义,其绝对值没有意义(定序值,而非定距数值)
- 校正预测的过程就是把模型输出概率值的校正成真实的概率的过程,使得校正后的概率有绝对值意义
自动特征管理(Automated Feature Management)
- 将特征空间描绘成上下文和语义信号,每个信号都可以被翻译成一个在学习时有真实值的特征集合
- [待更新]
一些不成功的实验记录(Unsuccessful Experiments)
本节记录google的一些失败的尝试方向(有些可能会让人很惊讶),这些方向模型没有明显收益
Aggressive Feature Hashing
关于特征哈希(Feature Hashing)的相关知识可参考Feature-Hashing
- Feature Hashing for Large Scale Multitask Learning论文指出,Feature Hashing方法效果显著
- 报告显示使用特征hashing技巧,可以能将学习一个垃圾邮件过滤模型的特征空间映射成包含\(2^24\)个特征的特征空间(疑问:这里的特征原来不止\(2^24\)个吗?)
- 但是实验证明,使用 Feature Hashing 方法并不能提升我们的方法,所以建议保留 interpretable(non-hashed)的特征向量
Dropout
- Google用网格搜索的方法测试了从0.1到0.5的Dropout特征丢弃概率
- 所有情况均没有带来任何收益(包括精度指标和泛化能力),还往往给模型带来损害(detriment)
- Google给出的一个解释是:Dropout在图像领域取得较好收益的原因是因为图像领域的数据特征分布与计算广告领域不同
- 图像领域:稠密特征,此时Dropout把结果(effect)从强相关的特征中分离开来,从而得到泛化效果更好的分类器
- 计算广告:稀疏特征,且有噪音
Feature Bagging
- 对特征进行overlapping采样(注意,样本Bagging和特征Bagging不同),然后训练多个独立的模型,最后取平均值
- 实验证明模型的的AucLoss降低了0.1%-0.6%
Feature Vector Normalization
- \(\mathbf{x} = \frac{\mathbf{x}}{||\mathbf{x}||}\)
- 开始有一点精度上的收益,但是后面也出现了一定程度的detriment
- Google的解释是可能是由于per-coordinate learning rates和正则化的影响
Hexo——Next主题搜索窗口无法弹出
问题描述
- 有时候会遇到在Mac上Next主题窗口无法弹出的问题
- 问题分为两类
- 一类为找不到
search.xml
文件:加载search.xml
时错误为404 - 另一类为文章中有特殊字符:加载
search.xml
检查时错误为304
- 一类为找不到
解决方案
404类
修改最外层配置文件
./_config.yml
,添加以下语句(实测这一步非必须)1
2
3
4
5search:
path: search.xml
field: post
format: html
limit: 10000安装搜索插件
1
npm install hexo-generator-searchdb --save
304类
- 304状态说明是加载文件存在,但是无法正常解析文件
- 直接用浏览器访问
search.xml
文件链接,然后查看文件解析异常出现在哪个地方,然后删除特殊字符即可- 个人理解,从哪个文件不能搜索,特殊字符就出现在哪个文件中
- 说明:目前还没遇到过这种情况,后面遇到会再补充
CA——Feature-Hashing
- 参考文献: Feature Hashing for Large Scale Multitask Learning
- 特征哈希(Feature Hashing)常用于数据特征降维,同时尽量保留原始特征的表达能力
论文贡献
- 给出了一种高维数据降维方法,特征哈希(Feature Hashing)
- 严格证明了特征哈希的可用性
背景
- 一种构造组合特征的方法是笛卡尔乘积
- 计算广告领域往往有数十亿的高维特征
- 一种表达方式是使用词表法,对每个特征从词表里面进行查询
- 缺陷一:拓展问题,每次拓展词表时难度较大(难以进行模型升级,因为特征维度在变化)
- 缺陷二:无法处理词表中不存在的特征(Unknown特征)
- 一般的降维方法容易带来特征表达能力的损失
特征哈希
哈希函数定义(参考自博客:https://blog.csdn.net/qjf42/article/details/82387559)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20def feature_hashing(features, m):
"""
Args:
features: 输入特征序列,可以是数字,字符串(本质还是数字)
m: 输出的特征维度,通常是2**26(vw),2**20(scikit-learn)
Returns:
m维的(稀疏)向量
"""
# 这里的x一般是稀疏表示的(如:scipy.sparse.csr_matrix),这里是为了方便说明
x = np.zeros(m)
for feature in features:
# hash_func_1保证散列尽量平均且散列速度快
idx = hash_func_1(feature) % m
# 这里在原始论文中
sign = hash_func_2(feature) % 2
if sign == 1:
x[idx] += 1
else:
x[idx] -= 1
return x- 输出特征维度一般为\(m = 2^24\)等,是一个认为给定的数字
与词表法比较:
- 解决了模型升级时的特征拓展问题(增加新特征时,特征的维度不会变化)
- 解决了Unknown特征问题(个人理解:因为hash函数不管是什么特征,都可以一视同仁)
- 无需查表,节省了查表的时间(个人理解:其实查表时一般实现方式也是用哈希表构建索引,所以这里不能算是优势)
- 完成了降维(这里是把字典法里面对邮件或者文档的id也算作一个特征,这个特征one hot表示一下将会造成数据维度变得非常大?但是id算做特征有什么意义吗?)
一些说明
- 冲突总会发生,也就是说不同一个特征总有一定的概率被映射到同一个维度(即两个不同特征的
idx
值可能相等)上 - Paper中的垃圾邮件过滤模型实验证明:冲突造成的损失漏召率在\(m=2^22\)时影响约为1%,接近不做hash时的效果(特征维度在不做hash约为\(2^{25}\))且在\(m=2^{18}\)时为1.12%,也只升高了一点点
- 另外:无论如何,总有特殊情况,比如重要的特征如用户的性别特征“男”和“女”二者可能被映射到同一个维度上
- 这里编码时是男:
(1, 0)
, 女(0, 1)
这样的,所以如果二者映射到同一个维度上,那么这两个特征丢失了原本的表达能力 - 真实环境中如果遇到这些问题将会很难调试,如果找到了相关的问题,可以通过修改映射函数的输入参数字符串等方式来错开两个特征
- 这里编码时是男:
- 特征哈希本身可以类比于机器学习中的核技巧,所以特征哈希也称为哈希技巧
一些理解
知乎用户
- 参考Ainika Peng的博客:https://www.zhihu.com/question/264165760/answer/279676705
- 一般而言这类技术是为了解决两个问题:
- 一是将categorical的特征编码为模型可理解的格式, 这是个基础问题。One-Hot Serializing就可以达到这个效果,例如将训练样本中出现过的的每个deviceid按顺序递增编号(比如deviceid@xxx:1 -> feature@10000:1)。
- 缺点1:这个映射表需要传递给引擎端,在prediction的时候照着再查一遍,数据量大且数据结构设计不好的时候很费时间;
- 缺点2:有些频次很低的特征置信度不高,单独出现对模型无益(甚至over-fitting)。这时候可以使用按频次截断技术进行降维。比如微软在deep crossing中提到的特征工程方法:只保留曝光最多的10k个campaign id编码为0-9999,其余的id全部编码为10000,但辅以poCTR等连续特征作为辅助。事实上这是一种手工的Hashing方法。
- 二是尽可能在保留有效信息的基础上降低训练和预测过程的时间复杂度
- 一是将categorical的特征编码为模型可理解的格式, 这是个基础问题。One-Hot Serializing就可以达到这个效果,例如将训练样本中出现过的的每个deviceid按顺序递增编号(比如deviceid@xxx:1 -> feature@10000:1)。
- 自动Hashing方法的好处是:
- 只要训练和预测时使用的hashing方法一致,对同一个特征的编码结果即一致,因此引擎预测或提供数据dump的时候无需查找编码表。所以其最大优点在于数据一致性和速度提升,这在极大规模特征和在线学习中至关重要。
- 我们说的Hashing算法一般而言均特意设计为低碰撞率。
- 因此一般hashing算法本身不会大幅降低特征维度,自然也不会大幅损失特征信息。真正可能存在问题的是hashing之后的降维过程。
- 一个非常常见的陷阱是string哈希到int64后取模m,试图将特征压缩至m维one-hot空间。在这种情况下,对于不知情的随机hashing过程,不同特征的碰撞率为1/m。举个例子,对于“性别”特征,将male哈希为一个int64,female哈希为另一个int64,很难发生碰撞;但如果你试图使用mod2将其压缩,如果你的算法哈希出的这两个int64奇偶性相同,则会导致特征失效。在你有很多feature需要哈希而又不清楚hashing算法细节的情况下,这在概率意义上是很容易发生的。
- 这里的mod2是极端举例,其实m的取值小于原始维度的情况下都有一定概率造成冲突
- 因此我们会更倾向于所谓的embedding算法
- 例如将70万维的userid通过weight embedding到32维的连续值特征上(不同于传统hashing的低维离散值特征)。这意味着训练过程更加复杂(有更多的weight需要optimize);但对于预测过程,其特征性能十分良好且时间复杂度得以降低。同时,由于连续值特征空间的表达能力大幅高于离散值特征空间,整个模型的表达能力并不会明显下降,也基本不会发生离散hashing的碰撞问题。
- 当然,如果是FM这类倾向于接受离散值的模型,手工serializing+精心设计的hashing是较好的选择。
- 优点:
- 训练和预测的时间复杂度大幅降低;
- 数据的一致性强,不存在同一个特征今天编码成这个、明天编码成那个的情况,便于跟踪单特征效果;
- 对new feature可以直接编码并加入训练,无需等待编码表统计并反馈;
- 降低feature space大小,(精心设计可以)降低over-fitting的几率。
- 缺点
- 在不清楚hashing function细节的情况下,容易导致特征碰撞失效,且难以排查;
- 难以通过hashing出的特征反推源特征;
- embedding会降低模型的可解释性。