精华内容
下载资源
问答
  • 【特征工程】特征衍生+案例

    千次阅读 2019-07-11 09:03:19
    特征衍生+案例

    在这里插入图片描述
    问:特征衍生上千、万的变量,是怎么做的?
    问:大家是如何衍生出成千上万个变量的?衍生变量是怎么生成的?

    研习社-上海-桂浩:
    请教一个问题,大家是如何衍生出成千上万个变量的?衍生变量是怎么生成的
    云何-simple:
    这是特征工程阶段所要做的事情
    研习社-上海-桂浩:
    基于时间的维度细分,组合一些基础变量等等
    研习社-杭州-小五:
    可以用sql,也可以用python,自己熟悉的就行啊
    研习社-杭州-小五:
    先自己写一个大概的衍生框架,然后根据框架写代码就好了
    云何-simple:
    需要衍生哪些特征 这个是重点

    关键词

      特征衍生、特征构建、合成特征、特征组合、自动化特征衍生

    特征衍生

      在实际业务中,通常我们只拥有几个到几十个不等的基础变量,而多数变量没有实际含义,不适合直接建模,如用户地址(多种属性值的分类变量)、用户日消费金额(弱数值变量)。而此类变量在做一定的变换或者组合后,往往具有较强的信息价值,对数据敏感性和机器学习实战经验能起到一定的帮助作用。所以我们需要对基础特征做一些衍生类的工作,也就是业内常说的如何生成万维数据。

      特征衍生也叫特征构建,是指从原始数据中构建新的特征,也属于特征选择的一种手段。特征构建工作并不完全依赖于技术,它要求我们具备相关领域丰富的知识或者实践经验,基于业务,花时间去观察和分析原始数据,思考问题的潜在形式和数据结构,从原始数据中找出一些具有物理意义的特征。

      找到可以拓展的基础特征后,便可用如下几种方式衍生特征:

    • 特征扩展
    • 合成特征
    • 特征组合
    • 特征交叉

      乍一听,挺难懂,这都什么东西,有什么区别?其实这些概念基本都一个意思,就一些小细节会有不同。有笔者说:合成特征 (synthetic feature)和特征组合(Feature Crosses)不太一样,特征交叉是特征组合的一个子集。

      我们今天,简单讲3个概念:

    1.特征扩展

      基于一个特征,使用特征值打平(扩展)的方式衍生多个标注类型的特征,也可以理解为离散化。对于分类变量,直接one-hot编码;对于数值型特征,离散化到几个固定的区间段,然后用one-hot编码。比如信贷场景逾期天数:

      这里可以起到两个作用:①把线性函数转换成分段阶跃函数,减少过拟合。 ②标注 ,方便后续特征交叉组合

    2.特征组合

      指将两个或多个输入特征通过数学运算进行组合。分为如下几种情况:

    • 数值运算
      • 如对特征进行加,减,乘,除
    • 特征交叉
      • 对多个特征进行交叉组合,或做交,并,补,笛卡尔集等运算。(可参考后面案例)
      • 暴力交叉,暴力交叉可能产生稀疏问题。

      在实践中,扩展线性模型时辅以特征组合一直都是训练大规模数据集的有效方法,机器学习模型很少会组合连续特征。不过,机器学习模型却经常组合独热特征矢量,将独热特征矢量的特征组合视为逻辑连接。

    3.合成特征

      合成特征的思想很简单,通过将单独的特征进行组合(相乘或求笛卡尔积)而形成的合成特征。是一种让线性模型学习到非线性特征的方式:包括以下类型:

    • 将一个特征与其本身或其他特征相乘(称为特征组合)。比如属性A有三个特征,属性B有两个特征,笛卡尔积后就有六个组合特征。
    • 两个特征相除。
    • 对连续特征进行分桶,以分为多个区间分箱。

      说明: 通过标准化或缩放单独创建的特征不属于合成特征。

      说明: 合成特征与组合特征关系在于:特征组合广义上包含合成特征,合成特征则改变了特征的线性关系,属于无中生有。

    自动衍生

      包括自动衍生和深度衍生的方法,可以缩减时间成本,构建维度更广更全面的新生特征。具体可以参考:Featuretools

    实操案例

      下面,我们基于用户特征扩展、特征组合等方法,对单个用户常见的运营商数据中的通话日志信息account_info,做一个特征衍生的案例。

      我们可以看到,用户通话信息宽表中的基础特征只有9个,而且在没做变换之前,多数特征不能直接使用。因此,我们用上述几种方法展开这个宽表。

    #特征衍生1,更改字段含义,离散化特征,去除边缘数据的影响
    tmp1['cutoff_date']      = self.cutoff_date
    tmp1['call_time']        = tmp1['call_time'].map(lambda x : int(x))
    tmp1['call_type_name']   = np.where(tmp1['call_type_name'] =='主叫','callout','callin')
    tmp1['call_land_type']   = tmp1[['call_address','contact_area']].apply(lambda x : 'local' if x['call_address'] == x['contact_area'] else 'inland',axis = 1)
    tmp1['call_time_type']   = tmp1['call_time'].map(lambda x : 'short' if int(x) <60 else 'midle' if int(x)<300 else 'long')
    tmp1['contact_type']     = tmp1['contact_type'].fillna('')
    tmp1['call_special']     = np.where(tmp1['contact_type'].str.contains('借贷'),'special','normal')
    tmp1['call_period']      = tmp1['call_start_time'].apply(lambda x: 'night' if 0<int(pd.to_datetime(x).strftime("%H")) <5 else 'day')
    

      可以看到,新增了call_land、call_type、call_time、call_period等字段(主被叫、本外地、时长、日夜间、特殊,行为习惯等判别依据 )

      之后,基于时间序列,做稀疏编码

    #特征衍生2,基于时间序列,做与cutofftime的稀疏编码,分别为:①距cutofftime的月份 ②距cutofftime 30,60,90,120,150,180 天内
    tmp1['freq'],tmp1['dtot']=1,1
    tmp1['diff_time'] =DT.calu_datediff2(indata=tmp1,date_1='cutoff_date',date_2='call_start_time')
    tmp1 = DT.bin_date(indata=tmp1,binlist=[30*v for v in [1,3,6,12] ],var='diff_time',varname='d')
    tmp1 = DT.bin_date2(indata=tmp1,binlist=[30,60,90,120,150,180],var='diff_time',varname='dt') 
    

      此时宽表的特征已经扩增到30+

      假设宽表的构建已基本完成,接下来就对该用户做基于时间序列和属性特征的交叉组合

    def call_info_feature1(self,indata):
        #主叫、本地、时长、夜间、特殊情况变量衍生
        tmp1=indata.copy()
        prefix = 'CALL'
        grp_var1,grp_var21,grp_var22,grp_var23,grp_var24 = ['call_type_name'],['call_land_type'],['call_time_type'],['call_special'],['call_period']
        var_name_list = ['freq']
        func_list     = [pd.Series.count]
        grp_dict_all  = ['total']
        grp_dict1 = [list({'callout':'callout','callin':'callin'})]
        for i in grp_dict1:
            grp_dict1_all = grp_dict_all + i 
        grp_dict21     = [list({'local':'local','inland':'inland','other':'other'})]
        for i in grp_dict21:
            grp_dict21_all = grp_dict_all + i 
        grp_dict22     = [list({'short':'short','midle':'midle','long':'long'})]
        for i in grp_dict22:
            grp_dict22_all = grp_dict_all + i 
        grp_dict23     = [list({'special':'special','normal':'normal'})]
        for i in grp_dict23:
            grp_dict23_all = grp_dict_all + i 
        grp_dict24     = [list({'night':'night','day':'day'})]
        for i in grp_dict24:
            grp_dict24_all = grp_dict_all + i 
        tmp_ds = pd.DataFrame()
        for i,j in zip([grp_var21,grp_var22,grp_var23,grp_var24],[grp_dict21_all,grp_dict22_all,grp_dict23_all,grp_dict24_all]):
            tmp_1 = DT.feature_derived1(indata = tmp1,prefix =prefix,grp_var1 = grp_var1,grp_var2 = i,var_name_list = var_name_list,func_list = func_list,grp_dict1_all = grp_dict1_all,grp_dict2_all = j).T # 主被叫、本地外地、长短时长
            tmp_ds = tmp_ds.append(tmp_1)
        tmp_ds = tmp_ds.T    
        tmp_ds['idvar'] = self.idvar
        return tmp_ds
    
    
    # 特征衍生函数
    def feature_derived1(self,indata,prefix,grp_var1,grp_var2,var_name_list,func_list,grp_dict1_all,grp_dict2_all):
        tmp_ds = indata.copy()   
        
        flag_list   = ['d30', 'd90','d180','d360','dtot']
        flag_series = ['dt0','dt1','dt2','dt3','dt4','dt5']
        col1=[f for f in flag_list+flag_series] 
        if flag_series != []:
            col2 = ["b{num}_{fun}".format(num=num,fun=fun)for num in [3,6] for fun in ['max', 'avg','sum']]
            col3 = ['bm13_rate'] 
        else:
            col2,col3 = [],[]
        for  n,input_var in enumerate(var_name_list):           
            for dt in flag_list+flag_series:
                tmp_ds[dt] = np.where(tmp_ds[dt]==1,tmp_ds[input_var],np.nan)
        tmp_ds['_total1_'] = 'total'
        tmp_1 = pd.DataFrame()        
        for gv in grp_var1 + ['_total1_']:
            tmp_1 = tmp_1.append(tmp_ds.rename(columns={gv:'grp_var1'}),ignore_index=True)
        tmp_1['_total2_']='total'
        tmp_2=pd.DataFrame()        
        for gv in grp_var2 + ['_total2_']:
            tmp_2=tmp_2.append(tmp_1.rename(columns={gv:'grp_var2'}),ignore_index=True)
        tmp_2=tmp_2.groupby(['grp_var1','grp_var2'])[[f for f in flag_list+flag_series]].agg(func_list).reset_index()
        for name in ['grp_var2','grp_var1']:
            if name not in tmp_2.columns:
                tmp_2[name]=np.nan
        tmp_2=tmp_2[['grp_var2','grp_var1'] +[f for f in flag_list+flag_series]]        
        tmp_2.columns=['grp_var2','grp_var1']+[f for f in flag_list+flag_series]
        
        if flag_series != []:
            for num in [3,6]:
                tmp_2['b{num}_max'.format(num=num)] =tmp_2[[f for f in flag_series][:num]].max(axis=1)
                tmp_2['b{num}_avg'.format(num=num)] =tmp_2[[f for f in flag_series][:num]].mean(axis=1)
                tmp_2['b{num}_sum'.format(num=num)] =tmp_2[[f for f in flag_series][:num]].sum(axis=1)
            tmp_2['bm13_rate']   =np.where( 
                    ((tmp_2[flag_series[1]] +tmp_2[flag_series[2]]).isnull()) | ((tmp_2[flag_series[1]] +tmp_2[flag_series[2]])==0),
                    0,100*2*tmp_2[flag_series[0]] /(tmp_2[flag_series[1]] +tmp_2[flag_series[2]]))
        tmp_2=tmp_2[['grp_var2','grp_var1'] + col1+col2+col3]
        
        tmp_3=pd.DataFrame(pd.pivot_table(tmp_2,values=col1+col2+col3,columns=['grp_var1','grp_var2'])).T
        
        columns_list = [(v1,v2,v3) for v3 in grp_dict2_all for v2 in grp_dict1_all for v1 in col1+col2+col3]
        for var_missing in [name for name in columns_list if name not in tmp_3.columns]:
            tmp_3[var_missing]=np.nan
        tmp_3=tmp_3[columns_list]
        tmp_3.columns=[prefix+"_"+name[2]+"_"+name[1]+"_"+ name[0] for name in tmp_3.columns]     
        return tmp_3
    
    

      运行,可以看到,衍生后,生成总计757个字段

      接下来,继续增加通讯录、联系人、短信、黑名单、标签等新的特征维度,用于交叉生成特征

    tmp_2 = self.call_info_feature2(indata = tmp1) # 通话记录详单、与通讯录匹配情况,构建用户社交画像。判断通讯录真实性,判断通话真实性,统计频繁联系人表单,输入催收系统
    tmp_3 = self.call_info_feature3(indata = tmp1) # 联系人contact_type命中标记:①警察②司法③贷款④催收等lable,识别账号社会风险。通过模糊匹配,精准匹配等异常标记进入本地名单库,识别本人风险
    tmp_4 = self.call_info_feature4(indata = tmp1) # 紧急联系人、通讯录、联系人,运用复杂网络、社团识别等技术,通过手机号命中黑名单、异常号码库。识别一度联系人风险,判断本人欺诈性
    

      依据经验,分析维度越多,衍生特征越多,这样,万维的数据就构建起来了。

      如今,生产环境中遇到离散特征衍生时的处理方式主要有两种:

    • ① 在做前期数据分析的时候,就将想要扩展和组合的数据提前处理好。
      • 优点:经验充分,扩展后的数据往往有较好的效果;
      • 缺点:人工处理,而且基本是写死成数据的,后期模型训练中不易调整。
    • ② 使用类似独热编码(One-Hot-Encoding)的方案,将特征值全量打开,实现特征的自动化扩展。
      • 优点:省时省力
      • 缺点:数据全量打开,以至过程和结果不可控,且可能存在无意义特征的爆炸导致不可计算或者计算效率低等。

      因此,我们提出一种较为合适的方法:将要处理的离散特征的特征值情况进行展现,然后基于其实际情况进行有选择可控制的特征自动化扩展和组合。

      方法如下:

    • 遍历产生离散特征值(自动)
    • 计算特征离散程度和各属性值占比,排序选择需要扩展的特征。(自动+手动)
    • 基于选择、处理后的特征值,扩展特征(自动)
    • 基于选择、处理后的特征值,组合特征(自动)
    • 特征量化
    • 特征规范化

    【参考】

    • 特征工程之自动特征生成(自动特征衍生)工具Featuretools介绍 汀桦坞 https://blog.csdn.net/wiborgite/article/details/88761330
    • 机器学习之特征组合、特征交叉 作者:Madazy 原文:https://blog.csdn.net/Madazy/article/details/84110400
    • 特征组合之DeepFM 作者:Madazy 原文:https://blog.csdn.net/Madazy/article/details/84337609
    • 特征组合之FFM 作者:Madazy 原文:https://blog.csdn.net/Madazy/article/details/84316840
    • 利用GBDT模型构造新特征 作者:Bryan__ 原文:https://blog.csdn.net/bryan__/article/details/51769118
    • FM及FFM算法 作者:陈玓玏 https://blog.csdn.net/weixin_39750084/article/details/83549027
    • 特征选择与特征组合 北冥有小鱼 https://blog.csdn.net/qq_26598445/article/details/80998760
    • 特征组合&特征交叉 (Feature Crosses) kugua233 https://segmentfault.com/a/1190000014799038
    • 机器学习之离散特征自动化扩展与组合 DemonHunter211 https://blog.csdn.net/kwame211/article/details/78109254
    • 自动特征工程 - AI科技大本营- https://blog.csdn.net/dQCFKyQDXYm3F8rB0/article/details/82392735
    • 深度特征合成:实现数据科学自动化 forever_24 https://blog.csdn.net/u014686462/article/details/84063667
    • 研习社-涛哥

      对数据分析、机器学习、数据科学、金融风控等感兴趣的小伙伴,需要数据集、代码、行业报告等各类学习资料,可添加微信:wu805686220(记得要备注喔!),也可关注微信公众号:风控圏子(别打错字,是圏子,不是圈子,算了直接复制吧!)

    关注公众号后,可联系圈子助手加入如下社群:

    • 机器学习风控讨论群(微信群)
    • 反欺诈讨论群(微信群)
    • python学习交流群(微信群)
    • 研习社资料(qq群:102755159)(干货、资料、项目、代码、报告、课件)

    相互学习,共同成长。

    展开全文
  • 分解-解决复杂问题的办法

    千次阅读 2019-02-28 17:33:34
    很多人知道刻意练习是最好的学习方法,不断重复...这里,重要的是理解分解这种思想,这种思想是解决系统问题的利器。 毕业快三年了,一直做软件开发的工作,一边工作一边读书学习。我发现,无论多么复杂的计算机系...

      很多人知道刻意练习是最好的学习方法,不断重复地学一项技能,直到学会为止。但是,如何重复地学习某种技能呢?

    答案是:将要完成的动作分解为多个彼此独立的小动作,重复地练习每个小动作,做到将每个小动作的要领长进脑子里,然后,重复训练整个动作。这里,重要的是理解分解这种思想,这种思想是解决系统问题的利器。

      毕业快三年了,一直做软件开发的工作,一边工作一边读书学习。我发现,无论多么复杂的计算机系统,都可以分解为彼此独立的小系统,大的系统不需要考虑每个子系统是如何实现的,只需要给每个子系统划定一个功能边界,各个子系统由不同的项目组去实现,最后,由这些小系统组成很复杂的系统。这种方法,用计算机的行话说,是"模块化"。你会发现,原来一个那么复杂的系统竟然是由很多简单的子系统组成的,这种现象叫涌现。

      具体到每个小系统内部,又是通过分解将很多子系统的功能划分为很多子模块,而子模块又划分为很多具体的实现方法。通过这么层层分解,将一个超级工程分解为很多独立的小项目,小到单个程序员能解决的程序,这样一个项目组的多个程序可以同时开工干活,通过并行地实现项目的每个小部分,极大地提高了工作效率。

      这种运用分解,将任务模块化的方法,是解决系统问题的最佳策略。这种策略告诉我们,要解决一个问题,不要一开始就陷入细节,先从整体上把握问题,把问题分解为几大方面,各个击破。历届中国领导人都强调:“抓主要矛盾”。不懂的人觉得这是假大空,真实的情况是,领导人在认知上比你高很多,云泥之别。看过一个故事,两个非洲的酋长比赛说大数,A说:“1”,B说:“2”,A接着说:“3”,B说:“你赢了”,因为非洲原始人不知道比3大的数。认知这东西,你比别人低了一个层次,眼界就差了十万八千里。

      那么,如何才能合理分解问题呢?

      你得在一个领域里接触到足够多的案例!为什么强调一万小时定律,就是因为在刻意练习的一万小时中,你会接触大量鲜活的案例,这些案例是什么,你会有个比较深刻的认识,包括这些案例的基本属性,某些成熟的解决方案。过去,一直听前辈说,你要在一个行业持续做10年左右,才能成为行业的精英,他也说不明白为什么要这么做,只是说,大家过去成功的经验是这样的。

      问题来了:如何实现一个桂圆系统呢?

       如果你没见过桂圆,你是无法完成这个项目的,因为你得知道桂圆的基本属性。一个桂圆,包括最外层的壳,里边的肉,和肉包裹的种子。如果要实现桂圆系统,你需要分别实现3个子系统:壳系统、肉系统、种子系统,然后,将这3个字体组合成一个整体的桂圆系统。至于3个子系统是如何实现的,你不要考虑,你得先关注大系统的实现需要完成哪些小系统,小系统自有别人来实现。就像你的公司今年要上市,那么上市就是个大系统,为了完成这个系统,需要解决几个大问题,那这几个大问题就是小系统,做为老板你不能亲自去完成每个小系统,你最大的任务就是思考要解决哪几个问题才能上市,努力的方向决定了结局。

    最后,“治大国如烹小鲜”,真不是在吹牛逼!

    展开全文
  • 预测值填充 常见kaggle的各种魔力操作,日常很少用 4.missing category 类别型变量的缺失可以直接形成一类 样本工程 上采样与下采样 上采样的意思多采集一些,下采样的意思是少采集一些 1> 针对正负样本不均衡问题,...

    已有特征的处理

    类别特征

    类别特征,表示某个数据点属于某一个类别,或具有某一种类的特性。一列类别特征,默认用自然数表示(可以用LabelEncoder将字符串转化为自然数)。如果一列类别特征里有K种不同类别,其取值范围是0到k01。

    例:颜色、性别、地址、血型、国籍、省、市、邮政编码。

    • 自然数编码

    将词表编码成自然数的过程,是将文字转化为数字的过程,没有做什么特殊处理。
    默认的编码方式(见上,使用sklearn 的LabelEncoder可以得到,也可以我们自己写代码得到),消耗内存小,训练时间快,但是特征的质量不高。
    比如站在不同模型的角度来考虑
    LR中将地点编码成1,2,3,4…自然数值大的带入wx+b得到的结果是较大的,这样是不合理的。
    另外一个是树模型,自然数编码就不会有影响,

    • 独热编码(One-hot Encoding)
      只有一个维度为1,其他维度都为0的编码方式

    如果类别特征本身有顺序(例:优秀、良好、合格、不合格),那么可以保留单列自然数编码。如果类别特征没有明显的顺序(例:红、黄、蓝),则可以使用以下方法:

    https://link.zhihu.com/?target=http%3A//scikit-learn.org/stable/modules/generated/sklearn.preprocessing.OneHotEncoder.html 用于类别特征的独热编码(One-Hot Encoding)。运行结果与LabelBinarizer相似,不过在参数以及输入输出的格式上有细微的差别,参见文档。输出的矩阵是稀疏的,含有大量的0。

    统计学中,独热编码的变种还有effects coding、contrast coding、nonsense coding等编码方式,但在数据挖掘中都不常用。

    类似的-> multihot—这种方式更加普遍

    实际使用时,onehot常常根据频次压缩维度(有损)
    适用场景:
    非常适配于LR的场景,绝对不能应用在树模型上面的。

    总结:
    自然数编码适用于树模型,独热编码适用于LR模型

    • 聚类编码

    和独热编码相比,聚类编码试图充分利用每一列0与1的信息表达能力。聚类编码时一般需要特定的专业知识(domain knowledge),例如ZIP码可以根据精确度分层为ZIP3、ZIP4、ZIP5、ZIP6,然后按层次进行编码。

    当onehot维度超级大的时候,可以先进行聚类,然后将聚类后的类做为新的类名

    (我个人尚未使用过这种方法,仅在读论文的时候看到了类似的思路,所以暂时不知道对于各种算法而言效果如何。)

    相关概念:特征哈希,将产生hash碰撞的特征分到一个桶里,这是一种无业务含义的有损压缩,通常应用在id(user id,商品id)类的场景。
    另外一种聚类方法是适用k-menas方法进行聚类

    操作方法:
    1> 哈希 + 类别型变量的obehot处理
    2> tensorflow等框架直接处理:tf.feature_column.categorical_column_with_hash_bucket

    • 平均数编码(mean encoding)
      来自于kaggle,使得结果的拟合速度更快,学习效果更好,是一个比较好用的处理数值型特征的方案。

    平均数编码(mean encoding),针对高基数类别特征的有监督编码。当一个类别特征列包括了极多不同类别时(如家庭地址,动辄上万)时,可以采用。优点:和独热编码相比,节省内存、减少算法计算时间、有效增强模型表现。

    对于分类问题:该特征取值下target的概率值
    对于回归问题:该特征取值下target的均值
    在这里插入图片描述

    • 只出现一次的类别

    在类别特征列里,有时会有一些类别,在训练集和测试集中总共只出现一次,例如特别偏僻的郊区地址。此时,保留其原有的自然数编码意义不大,不如将所有频数为1的类别合并到同一个新的类别下。

    注意:如果特征列的频数需要被当做一个新的特征加入数据集,请在上述合并之前提取出频数特征。

    数值型特征

    • 1.标准化

    使数值特征列的算数平均为0,方差(以及标准差)为1。不免疫outlier。
    链接:https://link.zhihu.com/?target=http%3A//scikit-learn.org/stable/modules/generated/sklearn.preprocessing.StandardScaler.html

    • 2.区间缩放(scaling)

    将一列的数值,除以这一列的最大绝对值。不免疫outlier。

    链接:https://link.zhihu.com/?target=http%3A//scikit-learn.org/stable/modules/generated/sklearn.preprocessing.MaxAbsScaler.html

    或:
    链接:https://link.zhihu.com/?target=http%3A//scikit-learn.org/stable/modules/generated/sklearn.preprocessing.MinMaxScaler.html

    • 函数变换法

    简单常用的函数变换法(一般针对于连续数据):平方(小数值—>大数值)、开平方(大数值—>小数值)、指数、对数、差分

    比如取log(最常用),将不具有正态分布的数据变换成具有正态分布的数据
    在这里插入图片描述
    在这里插入图片描述

    数值-类别的转换
    数值转类别:

    分桶离散化
    1>等频离散化
    2>等距离散化
    特征二值化
    类别转数值:target encoding / mean encoding

    特征构造

    1.统计值构造法

    指通过统计单个或者多个变量的统计值(max,min,count,mean)等而形成新的特征。

    方法:

    •单变量 如果某个特征与目标高度相关,那么可以根据具体的情况取这个特征的统计值作为新的特征。

    •多变量 如果特征与特征之间存在交互影响时,那么可以聚合分组两个或多个变量之后,再以统计值构造出新的特征。

    可统计的方式非常多:

    median(N1)_by(C1) \ 中位数
    mean(N1)_by(C1) \ 算术平均数
    mode(N1)_by(C1) \ 众数
    min(N1)_by(C1) \ 最小值
    max(N1)_by(C1) \ 最大值
    std(N1)_by(C1) \ 标准差
    var(N1)_by(C1) \ 方差
    freq(C2)_by(C1) \ 频数 
    

    例如:
    点击率预估问题下,用户有购买序列,每天对于电子商品都有点击pv,可以构造在10日前-5日前,用户电子商品点击pv
    销量预估
    二手房房价预估问题:房子:小区编号,该房子的公摊率 -> 构造:小区平均公摊率

    本方法不管在比赛还是日常都非常常用,比如信贷问题:
    在这里插入图片描述
    特征工程是非常重要的,业界有说法,**特征和数据决定了模型算法的上届,选模型和训练模型是为了逼近这个上界。**所以学习算法是重要的,更重要的是根据业务逻辑来吃什么样的数据进去。
    2.算术运算构造法

    即特征之间进行算术运算

    例如:X(featureA)/X(featureB),X(featureA)-X(featureB)等
    比如收藏的次数/点击的次数,可以计算收藏率
    下单的次数除以点击的次数,可以计算购买率

    二手房房价预估问题:房子:小区编号,该房子的公摊率 -> 构造:小区平均公摊率;该房屋公摊率与小区平均公摊率的差 ,这样构造的一个新的特征更有可能达到理想的上届。

    3.特征交叉

    指代类别特征之间的交叉
    手动的特征交叉:例如 女性 + 18岁-25岁 -> 购买美妆产品
    在这里插入图片描述
    比如上面性别和年龄分别为2维和5维,我们可以将这两个形成一个10维的onehot的交叉特征来对买口红的预测。在逻辑回归中,那个代表女性20-25岁的那个特征的权重是可以学习的更高一点的。
    到底选择谁做交叉也是跟业务的逻辑有关系的,

    FM模型自动交叉特征 
    

    4.模型抽取

    例如浅层决策树的叶子节点编号即可代表一个融合了其他特征的类别特征

    比如:数值特征的一次二值化相当于树分裂了一次;多次二值化

    再例如神经网络对特征可以自动抽取:比如RNN最后一个神经元的隐向量,是对于句子的编码;比如cnn本质是特征提取器

    模型:GBDT + LR,是feecbook在做他们的点击率预估时候使用的模型,使用GBDT对特征进行提取,LR做为学习算法
    可以理解为所有的机器学习算法都具有特征提取的能力,
    RNN,CNN都是由一个个函数拼接成的算数表达式,具有将一个输入向量表达转换为另外一个输出的向量表达。

    特征选择

    选择出来然后将其删除

    1.通过相关性分析
    计算相关性,然后将相关性低的进行删除
    例如:
    1> 分类问题:互信息
    2> 回归问题:皮尔森相关系数,看P值显著性/卡方检验

    2.wrapper包装法(没什么应用场景)

    类似随机森林,抽取特征子集,哪个子集的模型表现好留下哪个,容易过拟合,不经常用

    3.l1正则化
    集成在算法内部的特征筛选器

    利用l1正则化的特征选择能力

    4.通过树模型的增益

    树/提升树模型的:feature_importance

    5.特征降维

    信号数据,比如语音识别类,难以搞清楚每个维度含义的数据,可以使用PCA主成分分析来降维

    空值处理

    1.均值/统计值填充

    2.0值填充

    常用标准化后直接填充0值,方便快捷

    3.预测值填充

    常见kaggle的各种魔力操作,日常很少用

    4.missing category

    类别型变量的缺失可以直接形成一类

    样本工程

    上采样与下采样

    上采样的意思多采集一些,下采样的意思是少采集一些

    1> 针对正负样本不均衡问题,进行正样本的上采样或负样本的下采样(1:10)
    比如我们看抖音的完播率,我们可能看了50条只有一条看完了,将看完的做为正样本,没有看完的做为负样本,这样采样的时候一般将正样本多采集几次,而不是少采集负样本,因为负采样会造成信息的损失,并且一般在正采样之前会对负样本进行清洗。这种清洗是通过置信度进行清洗,比如将看了60%以下的进行剔除,只留下70%的负样本
    2> 样本按权重上采样/下采样 (or添加到损失函数)

    一般正负样本的采样比例会很影响学习的结果的,如果正负样本比例达到1:15,预测结果就会被负样本带跑偏,所以我们一般控制正负样本比例在1:10.

    指标的评估+特征工程的流程

    评价指标和函数的损失函数的评估是比较重要的,常常出现在面试过程中.
    sklearn中对于模型评估的介绍

    回归问题的模型评估:
    一般使用均方误差,对数均方误差,开根号的均方误差。

    分类算法的评估方法(sklean.metrics)

    以前我们在讲机器学习算法的时候,没有系统地讲过算法效果的评估方法,只是用精确度来做一个简单的评估,其实根据不同的应用场景,是可以选择更加合适的评估方法的。

    ​ 分类评估方法主要功能是用来评估分类算法的好坏,而评估一个分类器算法的好坏又包括许多项指标。了解各种评估方法,在实际应用中选择正确的评估方法是十分重要的。

    几个常用术语 ​ 这里首先介绍几个常见的模型评价术语,现在假设我们的分类目标只有两类,计为正例(positive)和负例(negative)分别是:

    1. True positives(TP): 被正确地划分为正例的个数,即实际为正例且被分类器划分为正例的实例数;
    2. False positives(FP): 被错误地划分为正例的个数,即实际为负例但被分类器划分为正例的实例数;
    3. False negatives(FN):被错误地划分为负例的个数,即实际为正例但被分类器划分为负例的实例数;
    4. True negatives(TN): 被正确地划分为负例的个数,即实际为负例且被分类器划分为负例的实例数。

    ​ 表1 四个术语的混淆矩阵

    在这里插入图片描述

    表1是这四个术语的混淆矩阵
    sklearn也是有可以直接使用的计算混淆矩阵的方法,拿到混淆矩阵的结果:
    在这里插入图片描述

    做以下说明:
    1)P=TP+FN表示实际为正例的样本个数。
    2)True、False描述的是分类器是否判断正确。
    3)Positive、Negative是分类器的分类结果,如果正例计为1、负例计为-1,即positive=1、negative=-1。用1表示True,-1表示False,那么实际的类标=TFPN,TF为true或false,PN为positive或negative。
    4)例如True positives(TP)的实际类标=1
    1=1为正例,False positives(FP)的实际类标=(-1)1=-1为负例,False negatives(FN)的实际类标=(-1)(-1)=1为正例,True negatives(TN)的实际类标=1*(-1)=-1为负例。
    拿到混淆矩阵之后我们就可以计算出几个衍生指标:
    评价指标

    1. **正确率(accuracy)**正确率是我们最常见的评价指标,accuracy = (TP+TN)/(P+N),正确率是被分对的样本数在所有样本数中的占比,通常来说,正确率越高,分类器越好。
      正确率不经常使用,使用场景为正负样本比较均衡的场景,如果正负样本不均衡,这个就会失去意义,比如预测火山爆发,即使正确率很高,但是没有实际的意义。
      在互联网领域,一个广告的点击率(CTR预估)也是在2%以下的,所以也不会使用正确率做为评价指标。

    2. **错误率(error rate)**错误率则与正确率相反,描述被分类器错分的比例,error rate = (FP+FN)/(P+N),对某一个实例来说,分对与分错是互斥事件,所以accuracy =1 - error rate。

    下面的灵敏度和特异性也是不太会常用的指标,

    1. 灵敏度(sensitivity)sensitivity = TP/P,表示的是所有正例中被分对的比例,衡量了分类器对正例的识别能力。

    2. 特异性(specificity)specificity = TN/N,表示的是所有负例中被分对的比例,衡量了分类器对负例的识别能力。

    我们平时工作中重点关注的一般是下面两个指标,精度和召回率,一般应用在评价信息检索的领域

    1. 精度(precision)precision=TP/(TP+FP),也叫查准率,精度是精确性的度量,表示被分为正例的示例中实际为正例的比例。

    2. 召回率(recall)也叫查全率召回率是覆盖面的度量,度量有多个正例被分为正例,recall=TP/(TP+FN)=TP/P=sensitivity,可以看到召回率与灵敏度是一样的。
      精度与召回率得计算说明:
      在这里插入图片描述
      现在三篇文章中,有文章1和文章2是关于OCR问题的其他都不是
      当阈值为0.8时,精度为2/2=100%,召回率为2/3=66%,
      当阈值为0.5时,精度为2/5=40%,召回率为2/3=66%
      精度和召回率是我们在整个模型预测完之后根据不同的正负样本划分阈值来做的一个评估,是跟划分阈值强相关的两个评价指标。

    召回率是一种宁可错杀100,不放过一个的方式,所以在预测一个人是否得了新冠时使用的就是召回率,所以不管是正负样本阈值的划分,还是模型的选择都更加关注召回率,如果逻辑回归模型的召回率高于树模型,我们就会偏向于选择逻辑回归模型,

    如果是预测地震,就要选择精度,宁可放过100,也不要错误预测一次,因为预测错一次对国民的影响是很大的。

    1. 其他评价指标计算速度:分类器训练和预测需要的时间;
      鲁棒性:处理缺失值和异常值的能力;
      可扩展性:处理大数据集的能力;
      可解释性:分类器的预测标准的可理解性,像决策树产生的规则就是很容易理解的,而神经网络的一堆参数就不好理解,我们只好把它看成一个黑盒子。

    2. 精度和召回率反映了分类器分类性能的两个方面。如果综合考虑查准率与查全率,可以得到新的评价指标F1-score,也称为综合分类率:F1=2×precision×recallprecision+recall ​F1=2×precision×recallprecision+recall​


    是精度和召回率的调和平均数。

    正确率能很好的评估分类算法吗(了解)

    ​ 不同算法有不同特点,在不同数据集上有不同的表现效果,根据特定的任务选择不同的算法。如何评价分类算法的好坏,要做具体任务具体分析。对于决策树,主要用正确率去评估,但是其他算法,只用正确率能很好的评估吗? ​ 答案是否定的。 ​ 正确率确实是一个很直观很好的评价指标,但是有时候正确率高并不能完全代表一个算法就好。比如对某个地区进行地震预测,地震分类属性分为0:不发生地震、1发生地震。我们都知道,不发生的概率是极大的,对于分类器而言,如果分类器不加思考,对每一个测试样例的类别都划分为0,达到99%的正确率,但是,问题来了,如果真的发生地震时,这个分类器毫无察觉,那带来的后果将是巨大的。很显然,99%正确率的分类器并不是我们想要的。出现这种现象的原因主要是数据分布不均衡,类别为1的数据太少,错分了类别1但达到了很高的正确率缺忽视了研究者本身最为关注的情况。

    什么样的分类器是最好的(了解)

    ​ 对某一个任务,某个具体的分类器不可能同时满足或提高所有上面介绍的指标。 ​ 如果一个分类器能正确分对所有的实例,那么各项指标都已经达到最优,但这样的分类器往往不存在。比如之前说的地震预测,既然不能百分百预测地震的发生,但实际情况中能容忍一定程度的误报。假设在1000次预测中,共有5次预测发生了地震,真实情况中有一次发生了地震,其他4次则为误报。正确率由原来的999/1000=99.9下降为996/1000=99.6。召回率由0/1=0%上升为1/1=100%。对此解释为,虽然预测失误了4次,但真的地震发生前,分类器能预测对,没有错过,这样的分类器实际意义更为重大,正是我们想要的。在这种情况下,在一定正确率前提下,要求分类器的召回率尽量高。

    模型评估

    模型评估常用方法?

    ​ 一般情况来说,单一评分标准无法完全评估一个机器学习模型。只用good和bad偏离真实场景去评估某个模型,都是一种欠妥的评估方式。下面介绍常用的分类模型和回归模型评估方法。

    分类模型常用评估方法:
    F1,ROC,AUC是综合的评估方法,尤其是AUC,比较重要

    在这里插入图片描述
    回归模型常用评估方法:
    在这里插入图片描述

    误差、偏差和方差有什么区别和联系

    在机器学习中,Bias(偏差),Error(误差),和Variance(方差)存在以下区别和联系:

    对于Error :

    • 误差(error):一般地,我们把学习器的实际预测输出与样本的真是输出之间的差异称为“误差”。

    • Error = Bias + Variance + Noise,Error反映的是整个模型的准确度。

    对于Noise:

    • 噪声:描述了在当前任务上任何学习算法所能达到的期望泛化误差的下界,即刻画了学习问题本身的难度。

    对于Bias:

    • Bias衡量模型拟合训练数据的能力(训练数据不一定是整个 training dataset,而是只用于训练它的那一部分数据,例如:mini-batch),Bias反映的是模型在样本上的输出与真实值之间的误差,即模型本身的精准度。
    • Bias 越小,拟合能力越高(可能产生overfitting);反之,拟合能力越低(可能产生underfitting)。
    • 偏差越大,越偏离真实数据,如下图第二行所示。

    对于Variance:

    在这里插入图片描述

    • Variance描述的是预测值的变化范围,离散程度,也就是离其期望值的距离。方差越大,数据的分布越分散,模型的稳定程度越差。
    • Variance反映的是模型每一次输出结果与模型输出期望之间的误差,即模型的稳定性。
    • Variance越小,模型的泛化的能力越高;反之,模型的泛化的能力越低。
    • 如果模型在训练集上拟合效果比较优秀,但是在测试集上拟合效果比较差劣,则方差较大,说明模型的稳定程度较差,出现这种现象可能是由于模型对训练集过拟合造成的。
      如下图右列所示。
      在这里插入图片描述

    经验误差与泛化误差

    经验误差(empirical error):也叫训练误差(training error),模型在训练集上的误差。

    泛化误差(generalization error):模型在新样本集(测试集)上的误差称为“泛化误差”。

    图解欠拟合、过拟合

    根据不同的坐标方式,欠拟合与过拟合图解不同。
    1.横轴为训练样本数量,纵轴为误差
    在这里插入图片描述
    如上图所示,我们可以直观看出欠拟合和过拟合的区别:

    ​ 模型欠拟合:在训练集以及测试集上同时具有较高的误差,此时模型的偏差较大;

    ​ 模型过拟合:在训练集上具有较低的误差,在测试集上具有较高的误差,此时模型的方差较大。

    ​ 模型正常:在训练集以及测试集上,同时具有相对较低的偏差以及方差。
    2.横轴为模型复杂程度,纵轴为误差

    在这里插入图片描述
    红线为测试集上的Error,蓝线为训练集上的Error

    ​ 模型欠拟合:模型在点A处,在训练集以及测试集上同时具有较高的误差,此时模型的偏差较大。

    ​ 模型过拟合:模型在点C处,在训练集上具有较低的误差,在测试集上具有较高的误差,此时模型的方差较大。

    ​ 模型正常:模型复杂程度控制在点B处为最优。
    3.横轴为正则项系数,纵轴为误差
    在这里插入图片描述
    红线为测试集上的Error,蓝线为训练集上的Error

    ​ 模型欠拟合:模型在点C处,在训练集以及测试集上同时具有较高的误差,此时模型的偏差较大。

    ​ 模型过拟合:模型在点A处,在训练集上具有较低的误差,在测试集上具有较高的误差,此时模型的方差较大。 它通常发生在模型过于复杂的情况下,如参数过多等,会使得模型的预测性能变弱,并且增加数据的波动性。虽然模型在训练时的效果可以表现的很完美,基本上记住了数据的全部特点,但这种模型在未知数据的表现能力会大减折扣,因为简单的模型泛化能力通常都是很弱的。

    ​ 模型正常:模型复杂程度控制在点B处为最优。

    如何解决欠拟合和欠拟合:

    如何解决欠拟合

    • 1.添加其他特征项。组合、泛化、相关性、上下文特征、平台特征等特征是特征添加的重要手段,有时候特征项不够会导致模型欠拟合。
    • 2.添加多项式特征。例如将线性模型添加二次项或三次项使模型泛化能力更强。例如,FM(Factorization Machine)模型、FFM(Field-aware Factorization
      Machine)模型,其实就是线性模型,增加了二阶多项式,保证了模型一定的拟合程度。
    • 3.可以增加模型的复杂程度。
    • 4.减小正则化系数。正则化的目的是用来防止过拟合的,但是现在模型出现了欠拟合,则需要减少正则化参数。

    如何解决过拟合:

    • 1.重新清洗数据,数据不纯会导致过拟合,此类情况需要重新清洗数据。
    • 2.增加训练样本数量。
    • 3.降低模型复杂程度。
    • 4.增大正则项系数。
    • 5.采用dropout方法,dropout方法,通俗的讲就是在训练的时候让神经元以一定的概率不工作。
    • 6.early stopping。
    • 7.减少迭代次数。
    • 8.添加噪声数据。
    • 9.树结构中,可以对树进行剪枝。
    • 10.减少特征项。

    欠拟合和过拟合这些方法,需要根据实际问题,实际模型,进行选择。

    交叉验证的主要作用

    ​ 为了得到更为稳健可靠的模型,对模型的泛化误差进行评估,得到模型泛化误差的近似值。当有多个模型可以选择时,我们通常选择“泛化误差”最小的模型。

    ​ 交叉验证的方法有许多种,但是最常用的是:留一交叉验证、k折交叉验证。

    理解k折交叉验证

    • 1.将含有N个样本的数据集,分成K份,每份含有N/K个样本。选择其中1份作为测试集,另外K-1份作为训练集,测试集就有K种情况。

    • 2.在每种情况中,用训练集训练模型,用测试集测试模型,计算模型的泛化误差。

    • 3.交叉验证重复K次,每份验证一次,平均K次的结果或者使用其它结合方式,最终得到一个单一估测,得到模型最终的泛化误差。

    • 4.将K种情况下,模型的泛化误差取均值,得到模型最终的泛化误差。

    • 5.一般2⩽K⩽10 。 k折交叉验证的优势在于,同时重复运用随机产生的子样本进行训练和验证,每次的结果验证一次,10折交叉验证是最常用的。

    • 6.训练集中样本数量要足够多,一般至少大于总样本数的50%。

    • 7.训练集和测试集必须从完整的数据集中均匀取样。均匀取样的目的是希望减少训练集、测试集与原数据集之间的偏差。当样本数量足够多时,通过随机取样,便可以实现均匀取样的效果。
      在这里插入图片描述
      在这里插入图片描述

    使用 train/test split, random_state=4
    X_train, X_test, y_train, y_test = train_test_split(X, y, random_state=4)

    评估模型的分类准确率
    knn = KNeighborsClassifier(n_neighbors=5)
    knn.fit(X_train, y_train)
    print(knn.score(X_test, y_test))

    改变 random_state=3
    X_train, X_test, y_train, y_test = train_test_split(X, y, random_state=3)

    评估模型的分类准确率
    knn = KNeighborsClassifier(n_neighbors=5)
    knn.fit(X_train, y_train)
    print(knn.score(X_test, y_test))

    from sklearn.cross_validation import KFold
    kf = KFold(25, n_folds=5, shuffle=False)

    打印每个训练集和测试集
    print(’{} {:^61} {}’.format(‘Iteration’, ‘Training set observations’, ‘Testing set observations’))
    for iteration, data in enumerate(kf, start=1):
    print(’{:^9} {} {:^25}’.format(iteration, str(data[0]), str(data[1])))

    from sklearn.neighbors import KNeighborsClassifier
    from sklearn.cross_validation import cross_val_score

    实例化KNN模型,KNN的K=5
    knn = KNeighborsClassifier(n_neighbors=5)

    10-fold cross-validation,cv=10
    scores = cross_val_score(knn, X, y, cv=10, scoring=‘accuracy’)
    print(scores)

    [ 1. 0.93333333 1. 1. 0.86666667 0.933333330.93333333 1. 1. 1. ]

    计算平均值
    print(scores.mean())

    0.966666666667

    k_range = list(range(1, 31)) # K的范围[1, 30]
    k_scores = [] # 存放每个K的评价结果
    for k in k_range:
    knn = KNeighborsClassifier(n_neighbors=k)
    scores = cross_val_score(knn, X, y, cv=10, scoring=‘accuracy’)
    k_scores.append(scores.mean())
    print(k_scores)

    [0.95999999999999996, 0.95333333333333337, 0.96666666666666656, 0.96666666666666656, 0.96666666666666679, 0.96666666666666679, 0.96666666666666679, 0.96666666666666679, 0.97333333333333338, 0.96666666666666679, 0.96666666666666679, 0.97333333333333338, 0.98000000000000009, 0.97333333333333338, 0.97333333333333338, 0.97333333333333338, 0.97333333333333338, 0.98000000000000009, 0.97333333333333338, 0.98000000000000009, 0.96666666666666656, 0.96666666666666656, 0.97333333333333338, 0.95999999999999996, 0.96666666666666656, 0.95999999999999996, 0.96666666666666656, 0.95333333333333337, 0.95333333333333337, 0.95333333333333337]

    ROC与AUC

    ​ ROC全称是“受试者工作特征”(Receiver Operating Characteristic)。

    ​ ROC曲线的面积就是AUC(Area Under Curve)。
    是在一个分类问题中根据概率预测值选择不同的阈值进行切分,计算出precision和recall,然后画出来图。

    一个二分类问题,我们都可以估计出一个事件的预估值,然后在分类时收到正负样本阈值划分的影响,对于新冠的预测,阈值可以设置为0.1,对于地震的预测可能就要设置为0.9,如果一个评估指标受到阈值的影响,那么这个评估指标的鲁棒性必然比较低,因此ROC和AUC就应运而生,

    ​ AUC用于衡量“二分类问题”机器学习算法性能(泛化能力)。

    ​ ROC曲线,通过将连续变量设定出多个不同的阈值,从而计算出一系列真正率和假正率(也可以说是设置不同的阈值,得到一系列混淆矩阵),再以假正率为横坐标、真正率为纵坐标绘制成曲线,曲线下面积越大,推断准确性越高。在ROC曲线上,最靠近坐标图左上方的点为假正率和真正率均较高的临界值。

    ​ 对于分类器,或者说分类算法,评价指标主要有Precision,Recall,F-score。下图是一个ROC曲线的示例。
    在这里插入图片描述
    ROC曲线的横坐标为False Positive Rate(FPR),纵坐标为True Positive Rate(TPR)。其中
    在这里插入图片描述
    下面着重介绍ROC曲线图中的四个点和一条线。 ​ 第一个点(0,1),即FPR=0, TPR=1,这意味着FN(False Negative)=0,并且FP(False Positive)=0。意味着这是一个完美的分类器,它将所有的样本都正确分类。 ​ 第二个点(1,0),即FPR=1,TPR=0,意味着这是一个最糟糕的分类器,因为它成功避开了所有的正确答案。 ​ 第三个点(0,0),即FPR=TPR=0,即FP(False Positive)=TP(True Positive)=0,可以发现该分类器预测所有的样本都为负样本(Negative)。 ​ 第四个点(1,1),即FPR=TPR=1,分类器实际上预测所有的样本都为正样本。 ​ 经过以上分析,ROC曲线越接近左上角,该分类器的性能越好。

    ​ ROC曲线所覆盖的面积称为AUC(Area Under Curve),可以更直观的判断学习器的性能,AUC越大则性能越好。

    如何画ROC曲线

    ​ 下图是一个示例,图中共有20个测试样本,“Class”一栏表示每个测试样本真正的标签(p表示正样本,n表示负样本),“Score”表示每个测试样本属于正样本的概率。

    步骤: 1、假设已经得出一系列样本被划分为正类的概率,按照大小排序。 2、从高到低,依次将“Score”值作为阈值threshold,当测试样本属于正样本的概率大于或等于这个threshold时,我们认为它为正样本,否则为负样本。举例来说,对于图中的第4个样本,其“Score”值为0.6,那么样本1,2,3,4都被认为是正样本,因为它们的“Score”值都大于等于0.6,而其他样本则都认为是负样本。 3、每次选取一个不同的threshold,得到一组FPR和TPR,即ROC曲线上的一点。以此共得到20组FPR和TPR的值。 4、根据3、中的每个坐标点,画图。
    在这里插入图片描述

    如何计算TPR,FPR

    1、分析数据 y_true = [0, 0, 1, 1];scores = [0.1, 0.4, 0.35, 0.8]; 2、列表
    在这里插入图片描述
    3、将截断点依次取为score值,计算TPR和FPR。 当截断点为0.1时: 说明只要score>=0.1,它的预测类别就是正例。 因为4个样本的score都大于等于0.1,所以,所有样本的预测类别都为P。 scores = [0.1, 0.4, 0.35, 0.8];y_true = [0, 0, 1, 1];y_pred = [1, 1, 1, 1]; 正例与反例信息如下:
    在这里插入图片描述
    由此可得: TPR = TP/(TP+FN) = 1; FPR = FP/(TN+FP) = 1;

    当截断点为0.35时: scores = [0.1, 0.4, 0.35, 0.8];y_true = [0, 0, 1, 1];y_pred = [0, 1, 1, 1]; 正例与反例信息如下:

    在这里插入图片描述
    由此可得: TPR = TP/(TP+FN) = 1; FPR = FP/(TN+FP) = 0.5;

    当截断点为0.4时: scores = [0.1, 0.4, 0.35, 0.8];y_true = [0, 0, 1, 1];y_pred = [0, 1, 0, 1]; 正例与反例信息如下:
    在这里插入图片描述
    由此可得: TPR = TP/(TP+FN) = 0.5; FPR = FP/(TN+FP) = 0;

    4、根据TPR、FPR值,以FPR为横轴,TPR为纵轴画图。

    如何计算AUC(ROC曲线的面积)

    •将坐标点按照横坐标FPR排序 。
    •计算第i个坐标点和第i+1 个坐标点的间距dx。
    •获取第i 或者i+1 个坐标点的纵坐标y。
    •计算面积微元ds=ydx。
    •对面积微元进行累加,得到AUC。

    ROC或者说AUC的优势
    不会受到正负样本不均衡的影响,因为他是统筹的考虑到了不同与执行下的情况

    为什么使用Roc和Auc评价分类器

    ​ 模型有很多评估方法,为什么还要使用ROC和AUC呢? ​ 因为ROC曲线有个很好的特性:当测试集中的正负样本的分布变换的时候,ROC曲线能够保持不变。在实际的数据集中经常会出现样本类不平衡,即正负样本比例差距较大,而且测试数据中的正负样本也可能随着时间变化。

    直观理解AUC

    ​ 下图展现了三种AUC的值:
    在这里插入图片描述

    ​ AUC是衡量二分类模型优劣的一种评价指标,表示正例排在负例前面的概率。其他评价指标有精确度、准确率、召回率,而AUC比这三者更为常用。 ​ 一般在分类模型中,预测结果都是以概率的形式表现,如果要计算准确率,通常都会手动设置一个阈值来将对应的概率转化成类别,这个阈值也就很大程度上影响了模型准确率的计算。 ​ 举例: ​ 现在假设有一个训练好的二分类器对10个正负样本(正例5个,负例5个)预测,得分按高到低排序得到的最好预测结果为[1, 1, 1, 1, 1, 0, 0, 0, 0, 0],即5个正例均排在5个负例前面,正例排在负例前面的概率为100%。然后绘制其ROC曲线,由于是10个样本,除去原点我们需要描10个点,如下:

    在这里插入图片描述

    两类分类问题对比来解释ROC

    在这里插入图片描述

    CTR 关注的是我们预测出来的一个列表样本客户是否点击了,我们不关心precision和recall,因为我们不知道样本是否点击了,以及用户点击了几个,我们关心的是排在头部的样本用户后面会点击,如果我们排在第一位的被点击了,说明正样本排在了负样本之前,我们这个推荐算法比较好,要是排在前面的没有被点击,用户而是点击了相对后面的样本,说明我们这个推荐算法做的不好。所以在一个排序问题转换为二分类问题中我们更关注AUC

    ​ 描点方式按照样本预测结果的得分高低从左至右开始遍历。从原点开始,每遇到1便向y轴正方向移动y轴最小步长1个单位,这里是1/5=0.2;每遇到0则向x轴正方向移动x轴最小步长1个单位,这里也是0.2。不难看出,上图的AUC等于1,印证了正例排在负例前面的概率的确为100%。

    ​ 假设预测结果序列为[1, 1, 1, 1, 0, 1, 0, 0, 0, 0]。

    在这里插入图片描述

    ​ 计算上图的AUC为0.96与计算正例与排在负例前面的概率0.8 × 1 + 0.2 × 0.8 = 0.96相等,而左上角阴影部分的面积则是负例排在正例前面的概率0.2 × 0.2 = 0.04。

    ​ 假设预测结果序列为[1, 1, 1, 0, 1, 0, 1, 0, 0, 0]。
    在这里插入图片描述

    计算上图的AUC为0.88与计算正例与排在负例前面的概率0.6 × 1 + 0.2 × 0.8 + 0.2 × 0.6 = 0.88相等,左上角阴影部分的面积是负例排在正例前面的概率0.2 × 0.2 × 3 = 0.12。

    AUC的计算方法(重要)

    参考链接

    1.按照正负pair对顺序概率计算 (基于正样本排在负样本前面的概率)
    在这里插入图片描述
    假设真实样本中有m个正样本,n个负样本,他们组合有mn中结果,每个样本都有一个预测的score(0.9,0.8…0.1),将正样本score大于负样本结果标记为1,将负样本score大于正样本的标记为0,正样本和负样本score相同的话标记为0.5,然后将这mn个数字相加然后再除以mn就是AUC,这种计算方式的时间复杂度是mn的,比较高

    2.根据list的顺序计算
    这个方法更加简单,也是sklearn背后使用的方法,
    在这里插入图片描述
    在这里插入图片描述
    在这里插入图片描述

    损失函数(重点)

    什么是损失函数

    ​ 损失函数(Loss Function)又叫做误差函数,用来衡量算法的运行情况,估量模型的预测值与真实值的不一致程度,是一个非负实值函数,通常使用L(Y,f(x))​
    L(Y,f(x))​
    来表示。损失函数越小,模型的鲁棒性就越好。损失函数是经验风险函数的核心部分,也是结构风险函数重要组成部分。

    常见的损失函数

    ​ 机器学习通过对算法中的目标函数进行不断求解优化,得到最终想要的结果。分类和回归问题中,通常使用损失函数或代价函数作为目标函数。 ​ 损失函数用来评价预测值和真实值不一样的程度。通常损失函数越好,模型的性能也越好。 ​ 损失函数可分为经验风险损失函数和结构风险损失函数。经验风险损失函数指预测结果和实际结果的差别,结构风险损失函数是在经验风险损失函数上加上正则项。 ​ 下面对损失函数做一个总结,需要知道这些损失函数都使用在了哪些算法中。

    (1)0-1损失函数 如果预测值和目标值相等,值为0,如果不相等,值为1。
    L(Y,f(x))={1,0, Y≠f(x)Y=f(x)L(Y,f(x))={1,Y≠f(x)0,Y=f(x)

    一般的在实际使用中,相等的条件过于严格,可适当放宽条件:

    L(Y,f(x))={1,0, |Y−f(x)|⩾T|Y−f(x)|<TL(Y,f(x))={1,|Y−f(x)|⩾T0,|Y−f(x)|<T

    感知机中应用的就是0-1损失,符合我们认知的损失,但是是阶跃的,不好优化,因此转化为其他的函数,所以我们认知的损失函数和算法优化的目标中间是存在代沟的,比如log loss,使用的交叉熵,但是这个交叉熵并不一定能够保证我们的precision和recall,在深度神经网络之前很少有机会让我们脱离算法来调节损失函数,在深度学习中,损失函数往往是我们自定义的,我们可以使用常规的损失函数,也可以是两个网络损失函数的带权融合,另外的话我们可以手动地在损失函数中加入正则或者其他东西,

    (2)绝对值损失函数 和0-1损失函数相似,绝对值损失函数表示为:
    L(Y,f(x))=|Y−f(x)|​L(Y,f(x))=|Y−f(x)|​

    (3)平方损失函数 (重要)
    L(Y,f(x))=∑ N (Y−f(x)) 2L(Y,f(x))=∑N(Y−f(x))2

    这点可从最小二乘法和欧几里得距离角度理解。最小二乘法的原理是,最优拟合曲线应该使所有点到回归直线的距离和最小。

    (4)对数损失函数 (也叫交叉熵损失,log loss,也叫负对数似然损失)
    L(Y,P(Y|X))=−logP(Y|X)L(Y,P(Y|X))=−log⁡P(Y|X)

    ​ 常见的逻辑回归使用的就是对数损失函数,有很多人认为逻辑回归的损失函数是平方损失,其实不然。逻辑回归它假设样本服从伯努利分布(0-1分布),进而求得满足该分布的似然函数,接着取对数求极值等。逻辑回归推导出的经验风险函数是最小化负的似然函数,从损失函数的角度看,就是对数损失函数。

    (6)指数损失函数 指数损失函数的标准形式为:
    L(Y,f(x))=exp(−Yf(x))L(Y,f(x))=exp⁡(−Yf(x))

    例如AdaBoost就是以指数损失函数为损失函数。

    (7)Hinge损失函数 Hinge损失函数的标准形式如下:
    L(y)=max(0,1−ty)L(y)=max(0,1−ty)

    统一的形式:
    L(Y,f(x))=max(0,Yf(x))L(Y,f(x))=max(0,Yf(x))

    其中y是预测值,范围为(-1,1),t为目标值,其为-1或1。
    在线性支持向量机中,最优化问题可等价于

    w,b min ∑ i=1 N (1−y i (wx i +b))+λ∥w∥ 2w,bmin∑i=1N(1−yi(wxi+b))+λ∥w∥2

    上式相似于下式

    1m ∑ i=1 N l(wx i +by i )+∥w∥ 21m∑i=1Nl(wxi+byi)+∥w∥2

    其中l(wx i +by i )是Hinge损失函数, ∥w∥2可看做为正则化项。

    逻辑回归为什么使用对数损失函数

    假设逻辑回归模型
    P(y=1|x;θ)=11+e −θ T xP(y=1|x;θ)=11+e−θTx

    假设逻辑回归模型的概率分布是伯努利分布,其概率质量函数为:
    P(X=n)={1−p,n=0p,n=1P(X=n)={1−p,n=0p,n=1

    其似然函数为:
    L(θ)=∏ i=1 m P(y=1|x i ) y i  P(y=0|x i ) 1−y iL(θ)=∏i=1mP(y=1|xi)yiP(y=0|xi)1−yi

    对数似然函数为:
    lnL(θ)=∑ i=1 m [y i lnP(y=1|x i )+(1−y i )lnP(y=0|x i )]=∑ i=1 m [y i lnP(y=1|x i )+(1−y i )ln(1−P(y=1|x i ))]ln⁡L(θ)=∑i=1m[yiln⁡P(y=1|xi)+(1−yi)ln⁡P(y=0|xi)]=∑i=1m[yiln⁡P(y=1|xi)+(1−yi)ln⁡(1−P(y=1|xi))]

    对数函数在单个数据点上的定义为:
    cost(y,p(y|x))=−ylnp(y|x)−(1−y)ln(1−p(y|x))cost(y,p(y|x))=−yln⁡p(y|x)−(1−y)ln⁡(1−p(y|x))

    则全局样本损失函数为:
    cost(y,p(y|x))=−∑ i=1 m [y i lnp(y i |x i )+(1−y i )ln(1−p(y i |x i ))]cost(y,p(y|x))=−∑i=1m[yiln⁡p(yi|xi)+(1−yi)ln⁡(1−p(yi|xi))]

    由此可看出,对数损失函数与极大似然估计的对数似然函数本质上是相同的。所以逻辑回归直接采用对数损失函数。

    梯度下降

    梯度下降法的种类:
    1.全样本内的梯度下降法,是对训练集中的每个样本算出一个梯度方向,然后再做平均算出所有样本内的梯度方向,这个梯度下降法计算复杂度较高,我们有多少个样本就要计算多少次,一次我们需要在性能和精确度中间做一个balance,我们更多使用的是下面两种梯度下降法
    2.随机梯度下降,每次只取一个样本,图像比较波动,正是因为这种波动性,随机梯度下降的好处是容易逃离鞍点,规避局部最小化的问题。
    3.批量梯度下降,每次取一小批样本,这个和全样本的梯度下降效果非常接近的,
    以后我们在使用tensorflow的tensorboard画图时,如果时批量梯度下降,那么图形将是比较平稳的缓慢下降,而如果选择随机梯度下降,图像将会时波动更大的,因为会收到单个样本的影响较大。
    在这里插入图片描述

    机器学习中为什么需要梯度下降

    梯度下降是机器学习中常见优化算法之一,梯度下降法有以下几个作用:

    (1)梯度下降是迭代法的一种,可以用于求解最小二乘问题。
    
    (2)在求解机器学习算法的模型参数,即无约束优化问题时,主要有梯度下降法(Gradient Descent)和最小二乘法。
    
    (3)在求解损失函数的最小值时,可以通过梯度下降法来一步步的迭代求解,得到最小化的损失函数和模型参数值。
    
    (4)如果我们需要求解损失函数的最大值,可通过梯度上升法来迭代。梯度下降法和梯度上升法可相互转换。
    
    (5)在机器学习中,梯度下降法主要有随机梯度下降法和批量梯度下降法。
    

    梯度下降法缺点

    梯度下降法缺点有以下几点:

    (1)靠近极小值时收敛速度减慢。
    
    (2)直线搜索时可能会产生一些问题。
    
    (3)可能会“之字形”地下降。
    

    梯度概念也有需注意的地方:

    (1)梯度是一个向量,即有方向有大小。 
    
    (2)梯度的方向是最大方向导数的方向。 
    
    (3)梯度的值是最大方向导数的值。
    

    梯度下降法直观理解

    梯度下降法经典图示如下图所示:

    在这里插入图片描述

    ​ 形象化举例,由上图所示,假如最开始,我们在一座大山上的某处位置,因为到处都是陌生的,不知道下山的路,所以只能摸索着根据直觉,走一步算一步,在此过程中,每走到一个位置的时候,都会求解当前位置的梯度,沿着梯度的负方向,也就是当前最陡峭的位置向下走一步,然后继续求解当前位置梯度,向这一步所在位置沿着最陡峭最易下山的位置走一步。不断循环求梯度,就这样一步步地走下去,一直走到我们觉得已经到了山脚。当然这样走下去,有可能我们不能走到山脚,而是到了某一个局部的山势低处。 ​ 由此,从上面的解释可以看出,梯度下降不一定能够找到全局的最优解,有可能是一个局部的最优解。当然,如果损失函数是凸函数,梯度下降法得到的解就一定是全局最优解。

    核心思想归纳:

    (1)初始化参数,随机选取取值范围内的任意数;
    
    (2)迭代操作: a)计算当前梯度; b)修改新的变量; c)计算朝最陡的下坡方向走一步; d)判断是否需要终止,如否,返回a);
    
    (3)得到全局最优解或者接近全局最优解。
    

    梯度下降法算法描述

    梯度下降法算法步骤如下:

    (1)确定优化模型的假设函数及损失函数。 ​ 举例,对于线性回归,假设函数为:
    在这里插入图片描述
    在这里插入图片描述

    如何对梯度下降法进行调优

    实际使用梯度下降法时,各项参数指标不能一步就达到理想状态,对梯度下降法调优主要体现在以下几个方面:

    (1)**算法迭代步长α 选择**。在算法参数初始化时,有时根据经验将步长初始化为1。实际取值取决于数据样本。可以从大到小,多取一些值,分别运行算法看迭代效果,如果损失函数在变小,则取值有效。如果取值无效,说明要增大步长。但步长太大,有时会导致迭代速度过快,错过最优解。步长太小,迭代速度慢,算法运行时间长。
    
    (2)**参数的初始值选择**。初始值不同,获得的最小值也有可能不同,梯度下降有可能得到的是局部最小值。如果损失函数是凸函数,则一定是最优解。由于有局部最优解的风险,需要多次用不同初始值运行算法,关键损失函数的最小值,选择损失函数最小化的初值。
    
    (3)**标准化处理**。由于样本不同,特征取值范围也不同,导致迭代速度慢。为了减少特征取值的影响,可对特征数据标准化,使新期望为0,新方差为1,可节省算法运行时间。
    

    随机梯度和批量梯度区别

    ​ 随机梯度下降(SDG)和批量梯度下降(BDG)是两种主要梯度下降法,其目的是增加某些限制来加速运算求解。 下面通过介绍两种梯度下降法的求解思路,对其进行比较。 假设函数为:
    在这里插入图片描述
    c) 随机梯度下降是通过每个样本来迭代更新一次。 随机梯度下降伴随的一个问题是噪音较批量梯度下降要多,使得随机梯度下降并不是每次迭代都向着整体最优化方向。

    小结: 随机梯度下降法、批量梯度下降法相对来说都比较极端,简单对比如下:
    在这里插入图片描述

    各种梯度下降法性能比较

    ​ 下表简单对比随机梯度下降(SGD)、批量梯度下降(BGD)、小批量梯度下降(Mini-batch GD)、和Online GD的区别:
    在这里插入图片描述

    BGD、SGD、Mini-batch GD,前面均已讨论过,这里介绍一下Online GD。

    ​ Online GD于Mini-batch GD/SGD的区别在于,所有训练数据只用一次,然后丢弃。这样做的优点在于可预测最终模型的变化趋势。

    ​ Online GD在互联网领域用的较多,比如搜索广告的点击率(CTR)预估模型,网民的点击行为会随着时间改变。用普通的BGD算法(每天更新一次)一方面耗时较长(需要对所有历史数据重新训练);另一方面,无法及时反馈用户的点击行为迁移。而Online GD算法可以实时的依据网民的点击行为进行迁移。

    常见的类别不平衡问题解决方法(重点)

    常见的CTR中正负样本的比例可能是1:100的,这种iu是嫉妒不平衡的。

    为什们要解决正负样本不平衡的问题呢?
    在这里插入图片描述
    以log loss为例,如果我们不做处理,我们就会过度的考虑到了负样本的影响,也就是说模型过多的学习到了为什么这个信息不被用户点,而不是这个信息为什们用户点击了的信息,因为这个时候敷衍本对模型的贡献过大,所以我们这个时候就需要对正负样本不均衡问题做已解决,解决方案如下。

    防止类别不平衡对学习造成的影响,在构建分类模型之前,需要对分类不平衡性问题进行处理。主要解决方法有:

    1、扩大数据集
    

    ​ 增加包含小类样本数据的数据,更多的数据能得到更多的分布信息。

    2、对大类数据欠采样(负样本的下采样)
    

    ​ 减少大类数据样本个数,使与小样本个数接近。 ​ 缺点:欠采样操作时若随机丢弃大类样本,可能会丢失重要信息。 ​ 代表算法:EasyEnsemble。其思想是利用集成学习机制,将大类划分为若干个集合供不同的学习器使用。相当于对每个学习器都进行欠采样,但对于全局则不会丢失重要信息。

    3、对小类数据过采样(正样本的上采样)
    

    ​ 过采样:对小类的数据样本进行采样来增加小类的数据样本个数。

    ​ 代表算法:SMOTE和ADASYN。

    ​ SMOTE:通过对训练集中的小类数据进行插值来产生额外的小类样本数据。

    ​ 新的少数类样本产生的策略:对每个少数类样本a,在a的最近邻中随机选一个样本b,然后在a、b之间的连线上随机选一点作为新合成的少数类样本。
    ​ ADASYN:根据学习难度的不同,对不同的少数类别的样本使用加权分布,对于难以学习的少数类的样本,产生更多的综合数据。 通过减少类不平衡引入的偏差和将分类决策边界自适应地转移到困难的样本两种手段,改善了数据分布。

    4、使用新评价指标(比如使用ROC评估方案,而不是使用F1)
    

    ​ 如果当前评价指标不适用,则应寻找其他具有说服力的评价指标。比如准确度这个评价指标在类别不均衡的分类任务中并不适用,甚至进行误导。因此在类别不均衡分类任务中,需要使用更有说服力的评价指标来对分类器进行评价。

    F1-score使用的场景是正负样本1:3一下,如果大于这个比例一般都是只考虑AUC的。

    5、选择新算法
    

    ​ 不同的算法适用于不同的任务与数据,应该使用不同的算法进行比较。

    6、数据代价加权(适用于神经网络中)
    

    ​ 例如当分类任务是识别小类,那么可以对分类器的小类样本数据增加权值,降低大类样本的权值,从而使得分类器将重点集中在小类样本身上。
    总结来说就是,可以在负样本前加上0.1的权重,正样本不做处理,这样的处理其实是对负样本做了打压,如果我们直接丢掉一些负样本是会损失掉部分信息的,因此数据代价加权是比较合理的处理方式。

    7、转化问题思考角度
    

    ​ 例如在分类问题时,把小类的样本作为异常点,将问题转化为异常点检测或变化趋势检测问题。 异常点检测即是对那些罕见事件进行识别。变化趋势检测区别于异常点检测在于其通过检测不寻常的变化趋势来识别。

    8、将问题细化分析
    

    ​ 对问题进行分析与挖掘,将问题划分成多个更小的问题,看这些小问题是否更容易解决。

    kaggle题目-波士顿放假啊预测方案

    kaggle竞赛和实际工作中的应用是非常像的,就差上线了。下面就以一道kaggle竞赛的赛题来说明如何抽象一个问题,如果做指标评估进行说明。

    补充知识:

    模型集成方案有三种,

    • 一种是不带权重的简单平均集成,
    • 另外一种是带权平均,认为的去设置权重,对效果好的模型设置较大的权重,对效果不太好的模型设置较小的权重,这种设置有人主观的因素在里面,也会存在偏差。
    • 另外是一种kaggle中常用的带权的集成方法—stacking,这是一种通过model来确定怎么融合。比如拿线性回归来说,我们可以拿样本预测值和真实样本做对比计算出正确率,然后再根据正确率给与不同的权重。
      第二层模型一般选择简单的模型,因此线性回归就经常做为第二层模型。
      使用stacking模型实现过程比较复杂。

    stacking模型图:

    在这里插入图片描述

    1,使用k折交叉验证对训练集进行打分,每一次k折使用要给模型
    2.然后我们会得到每个模型下每个样本的predict-score

    3.然后将五个模型做为分类属性,得分做为属性值。
    4.假设初始train中模型的size是(1000,100)–1000个样本,100个属性值,test中模型size是(500,100),那么第二层模型中的train size为(1000,5)—1000个样本,5中基模型,test size是(500,5)
    5.然后再用一个简单的模型(比如线性规划)来训练模型,得到的结果是不同模型之间的关系


    此链接为对波士顿房价预测的数据和代码部分:

    展开全文
  • 浅谈人工智能时代下的工程伦理问题

    万次阅读 多人点赞 2021-01-09 23:29:25
    浅谈人工智能时代下的工程伦理问题 一、引言 近年来,随着大数据基础设施建设以及人工智能技术的发展,社会中涌现出许多新技术,给人们带来更便捷的生活。但与其共生的道德风险问题也日益显著。人工智能道德风险即...

    浅谈人工智能时代下的工程伦理问题

    一、引言

    近年来,随着大数据基础设施建设以及人工智能技术的发展,社会中涌现出许多新技术,给人们带来更便捷的生活。但与其共生的道德风险问题也日益显著。人工智能道德风险即人工智能技术带来的伦理结果的不确定性,其既有主观因素也有客观因素,具体表现有道德算法风险、道德决策风险、隐私数据泄露风险等。风险主要成因有技术主体、政治、经济、文化等社会因素。结合当下大数据驱动的人工智能算法特点,如何运用风险治理思想分析其背后的工程伦理问题对人工智能领域发展具有重要意义。

    二、人工智能时代的当下

    在1956年达特茅会议中AI这个概念被提出,经历数次低谷与发展浪潮,人工智能再次活跃在大众的视野中,并且以更完备的生态以及更强的活力积极改变我们的生活。在如今的人工智能浪潮中,深度学习因为其能够胜任更复杂、更庞大的场景而成为主流。

    在AI的应用层面,随着大数据基础设施建设的日趋完备,人工智能孕育出许多产业,如:数据挖掘、人脸识别、语音识别、自动驾驶等。同时医疗卫生、交通运输、仓储物流、游戏等行业都已经或正在接受人工智能的优化。

    2019年11月11日24时整,“双11”全天的物流订单量达到创纪录的12.92亿元,物流订单量迎来了“爆炸式”的增长。“双11”全天各邮政、快递企业共处理5.35亿快件,是二季度以来日常处理量的3倍,同比增长28.6%,再创历史新高。而在其背后做支撑的是一套完整的基于大数据的人工智能系统。

    目前,百度、阿里、腾讯、谷歌等主流互联网公司正在大力投资人工智能相关产业与技术,而与此同时全球正有上千家公司全力押注人工智能,并且这个趋势依旧保持稳定增长的速度。

    三、人工智能伦理问题日益凸显

    显然,在当下这个人工智能技术飞速发展的时代,人工智能技术的广泛应用为人类带来了显而易见的好处。但技术的进步不但扩大了人类对于技术的恐慌,同时也放大了由于某些技术缺陷和忽略道德伦理问题而带来的负面影响。

    3.1 忽略伦理问题下产生的算法歧视问题

    外卖作为当下快节奏生活的必需品,在其背后做支撑的是数以百万的外卖员和强大的人工智能系统。2020年9月8日,一篇名为《外卖骑手,困在系统里》的文章在互联网上被热议,文章指出:2016至2019年间,美团多次向配送站站长发送加速通知,3公里的送餐距离最长时限一再被缩短至38分钟;而根据相关数据显示,2019年中国全行业外卖订单单均配送时间较3年前减少了10分钟。外卖骑手在系统算法与数据的驱动下疲于奔命,逐渐变成高危职业——骑手为在算法规定的最长送餐时限内完成送餐任务无视交通规则,不断提高车速。

    许多伦理问题都是由于实践主体缺乏必要的伦理意识造成的,而外卖平台算法使得外卖骑手被“困在系统里”显然是工程的决策者以及管理者没有考虑相关的伦理问题所导致的。外卖平台作为一项服务消费者、向社会提供就业岗位的工程,其目的与其他类型的工程类似,均为满足人类在某方面的需求,但工程在向社会提供服务的同时不应当忽略工程风险问题。

    3.2 从风险与安全角度分析外卖平台

    工程风险的防范与安全分为工程的质量监理与安全、意外风险控制与安全和事故应急处置与安全三个方面,分析外卖平台的工程风险主要从意外风险控制和事故应急处置两方面展开。

    3.2.1 意外风险控制维度的工程风险

    外卖平台作为服务大众的工程项目,其受众人数巨大——外卖市场规模超6500亿元,覆盖4.6亿消费者,工程一旦出现意外风险控制不当的情况则对其受众造成无法估量的损失。在基于大数据的人工智能算法的训练过程中,算法训练结果会随着数据重心的整体偏移,从而导致外卖骑手不得不加快派送的速度进而风险增加。因此,为避免人工智能系统追求极致地无限制缩短派送最长时限,工程师和程序设计者在程序设计之初应当添加阈值以保证外卖平台背后的外卖骑手能够在遵守交通规则的前提下及时、安全地完成任务。

    3.2.2 事故应急处置维度的工程风险

    事故应急处理体现着工程负责人、相关利益反对工程的理解程度。应对工程事故,应当事先准备一套完整的事故应急预案,保证迅速、有序地开展应急与救援行动,降低人员伤亡和经济损失。外卖骑手因忽视交通规则造成伤亡的事件并非最近才发生——2017年上半年,上海市公安局交警总队数据显示,在上海,平均每2.5天就有1名外卖骑手伤亡。同年,深圳3个月内外卖骑手伤亡12人。2018年,成都交警7个月间查处骑手违法近万次,事故196件,伤亡155人次,平均每天就有1个骑手因违法伤亡。2018年9月,广州交警查处外卖骑手交通违法近2000宗,美团占一半,饿了么排第二。而外卖平台除口头告诫骑手之外并没有推出从根本处解决问题的措施,直到《人物》发表《外卖骑手,困在系统里》一文后外卖平台才相继推出多等5分钟的政策。

    3.3 从工程四要素角度分析外卖平台

    工程包括技术要素、利益要素、责任要素、环境要素以及伦理要素,接下来将从工程四要素中的技术、利益与责任这三个方面来展开。

    3.3.1 技术维度的道德风险

    基于算法和大数据的人工智能技术背后隐藏着风险。算法体现着工程师和程序设计者的思想,其政治立场和社会偏见都会不可避免的嵌入程序中。从大数据中诞生的人工智能系统通常会存在基于数据采样偏差带来的问题,而这类问题在后续的训练中不会被消除甚至可能被放大。因此,为消除算法与数据采用带来的偏见,工程师以及程序设计者在程序设计之初就应当消除主观偏见;同时在数据的处理方法中,应当极尽全力保证数据的准确,降低数据偏差带来的风险。

    3.3.2 利益维度的道德问题

    人工智能存在威胁、侵犯人类利益的风险。从安全角度来说,人工智能应当对人类来说是安全的、可靠的、不作恶的。以外卖平台派单系统为例,外卖骑手在系统的算法歧视下被迫忽视交通规则,对骑手、对行人已经构成严重的安全隐患。因此,如何通过人工智能系统,在权衡各方利益、兼顾效率、保证安全的前提下实现利益最大化是人工智能系统需要解决的核心问题。

    3.3.3 责任维度的道德风险

    人工智能在价值选择困境与责任承担困境中存在风险。外卖平台派单系统在消费者对于外卖的时间要求与外卖骑手在派送过程中的风险问题之间面临抉择,系统应当尽量满足消费者的需求而忽视外卖骑手的安全,还是应当在尽量保护骑手的安全的前提下提高派送效率?在人工智能系统作为自主行为主体的情况下,系统会逐渐压缩骑手的安全空间。而在发生事故之后的责任鉴定中,系统并没有能力为自己的决策承担其相应的责任。

    四、总结

    为避免人工智能出现无节制的追求极致从而导致技术、利益、责任等方面的道德风险,实现人类社会可持续发展的目标,人工智能的设计应当秉承着将人类健康、安全和福祉放在首位的原则。由外卖平台人工智能系统这一例所引发出来的思考,进一步提出以下建议:

    1、工程设计之初应当强化工程负责人、管理者、工程师以及程序设计者的伦理意识。由于算法、工程体现着设计人员的思想,而相关人员对伦理方面的意识缺失必将导致缺乏伦理思想的工程存在缺陷。

    2、强化工程相关人员的风险与安全意识。风险与安全始终是工程无法逃避的问题,针对风险可接受性进行完备分析与评估,并对一系列不可控意外风险制定相关预警机制与应急机制是控制风险、规避风险、妥当处理事故的唯一途径。

    3、强化人类主导和监督能力。人类主导以及人为监督有助于人工智能系统不会走向极端,从而出现逻辑上无比正确却存在人类伦理问题的缺陷。

    4、明确人工智能系统的责任归属。程序设计之初应当对程序设计者针对不同模块的设计明确责任归属,当下人工智能的发展远远没有达到成熟阶段,相应的人工智能系统也没有能力对其发展的不良后果负责,这个责任很自然的需要其背后的软件工程师、程序设计者、工程负责人以及管理者共同承担;人工智能系统在设计阶段明确责任归属有利于工程事故发生之后的责任归属划分;有利于在程序设计阶段强化工程师们的工程伦理意识。

    从技术发展的角度来看,人工智能系统因其发展历史较短、技术成熟度低等原因远未达到可以完全信赖的地步。 人工智能系统在设计中应考虑预防性安全措施来防范风险,减少不可接受的伤害。

    展开全文
  • 你是否正在被复杂的业务逻辑折磨?是否有时觉得应用开发没意思、没挑战、技术含量低?其实,应用开发一点都不简单,也不无聊,业务的变化比底层基础实施的变化要多得多,封装这些变化需要很好的业务理解力,抽象能力...
  • 计算机考研复试面试常问问题 软件工程

    千次阅读 多人点赞 2020-04-17 21:06:50
    计算机考研复试面试常问问题 软件工程篇 使用前需知(拒绝白嫖,从你我做起,你只需点个赞就行): 需要pdf直接打印版,可在公众号"程序员宝藏"回复复试上岸获取(会持续更新) 在复习过程中,我用心查阅并整理了...
  • 本文给出Android延迟加载综合案例,描述ListView和ImageView的分页延迟加载,已经若干有用的封装技术,来结束本系列文章。 本文将在ListView延迟加载示例工程的基础上进行修改,加入图片延迟加载的功能。 在行布局...
  • 案例上手 Python 数据可视化

    万次阅读 多人点赞 2019-02-27 23:30:05
    20 个案例贯穿各个工具的学习过程 基于 GUI / HTML / Web 网站多种绘图风格 中、美、日三国不同思想的制图工具 从静态到交互,满足不同需要的图示 课程背景 数据可视化是数据分析和机器学习的重要环节,比如...
  • 职业规划-IT方向(超详细,超具体

    万次阅读 多人点赞 2019-06-21 21:30:13
    比如我每天下班还比较早,所以每天晚上都会自己做饭,因为会有些复杂一点的菜,像酸菜鱼、啤酒鸭、水煮肉片,所以长达一两个小时。在此过程中,我会一边做饭,一边听歌,很是惬意。最后看到自己烹饪出来的美味,颇有...
  • 一些具体的常见的失败原因: 不切实际或者不明确的项目目标; 对项目所需要的资源估算不准确; 需求不明确或者频繁变更; 没有对风险进行有效管理; 和客户之间沟通不畅; 无法解决项目的复杂性; ...
  • 上一篇博客提到,REST Client的方式整合的项目实现复杂的查询比较麻烦,实现的方法是需要我们自己根据ES的语法写出符合语法的bean来,然后把这个bean发送http请求给服务端,这种方法也是我以前参与的一个项目的做法...
  • 案例使用的数据为...此案例为不平衡二分类问题,目标为最大化auc值(ROC曲线下方面积)。目前此比赛已经结束。 竞赛题目链接为: https://www.kaggle.com/c/santander-customer-satisfaction 2.建模思路 本文档...
  • 这是作者网络安全自学教程系列,主要是关于安全工具和实践操作的在线笔记,特分享出来与博友们学习,希望您喜欢,...这篇文章将分享APT攻击检测溯源与常见APT组织的攻击案例,并介绍防御措施。希望文章对您有所帮助~
  • 考研复试面试问题---软件工程

    千次阅读 2020-05-05 16:17:25
    1、什么是软件工程?目前有哪几种主要的软件工程方法?概括地说,软件工程是指导计算机软件开发和维护的一门工程学科.采用工程的概念、原理、技术、和方法来开发与维护软件,把经过时间考验而证明正确的管理技术和当前...
  • 知识图谱关键技术与应用案例

    万次阅读 多人点赞 2018-11-06 11:50:18
    达观在知识图谱构建方面的经验、心得和相关案例。 一、知识图谱的概述 我们先直观的来看一下什么是知识图谱,下面有一张图,从这张图里可以看到,这个图里圆圈是节点,节点之间有一些带箭头的边来连成,这个节点实际...
  • 软件工程导论—软件与软件工程

    千次阅读 多人点赞 2020-05-02 12:47:35
    文章目录1. 软件与软件危机1.1.... 软件工程学2.1. 软件工程学的概念2.2. 软件工程项目的基本目标2.3. 软件工程的八项原则2.4. 软件工程的本质特征2.5. 软件工程的七条基本原理3. 软件工程方法学3.1. 软件工程方法...
  • 区块链+各行业应用案例

    万次阅读 多人点赞 2019-07-25 22:03:44
    文章目录区块链 + 金融区块链 + 电商区块链 + ...案例一:央行区块链数字票据交易平台   中国人民银行推动的基于区块链的数字票据交易平台测试成功,据了解,节后央行旗下的数字货币研究所也将正式挂牌。这意味着...
  • 软件项目管理案例分析

    千次阅读 2014-01-16 15:36:43
    为建立符合中国国情的软件开发过程和组织体系,培训中心特举办“软件项目管理案例分析”培训班,具体事宜通知如下: 一、培训对象 软件开发机构高级管理人员、项目经理、系统架构师、系统分析师、资深开发人员、...
  • Android 组件化案例

    千次阅读 2017-01-18 11:28:57
    Android组件化案例
  • 推荐系统从入门到 Spark 案例实践

    千次阅读 2018-11-26 13:17:09
    这里我们将对推荐,或者更确切的说是推荐系统有个更全面的认知,比如它的组成结构,涉及到哪些需要解决的技术问题、哪些技术领域,以及这些问题具体表现等。 推荐系统概述 在上篇中,我们看到了很多推荐的应用场景...
  • SkyForm CMP管理异构资源池案例

    万次阅读 2016-05-30 09:27:03
    OpenStack 社区版,具体版本为Icehouse,主机数量小于12台,系统为Ubuntu 12,承载了客户MIS系统的办公虚拟机。 OpenStack 商业版,后期采购的OpenStack商业版,主机数量大于70台,系统为CentOS 7.0,承载A公司研发...
  • Python实现运维案例

    千次阅读 2019-05-09 17:31:24
    案例分析 概述 Python是一种跨平台编程语言,在多种平台都能得到很好的支持,在各种平台环境的运维过程中,有些工作是很繁琐重复的工作,可以编写脚本作为工具辅助运维工作,比如linux中使用shell脚本,但是shell...
  • 四个架构设计案例及其思维方式

    千次阅读 2019-02-11 12:45:51
    架构的本质是管理复杂性,抽象、分层、分治和演化思维是我们工程师/架构师应对和管理复杂性的四种最基本武器。 在上一篇架构之道~四种核心架构思维中,我先介绍了抽象、分层、分治和演化这四种应对复杂性的基本武器...
  • 本文是11月17日大数据杂谈群分享的内容。...大家好,我来自天云大数据公司,我叫马敬涛,主要从事数据科学应用方面的工作。今天我给大家分享的主题是...复杂网络概念及价值在开始之前,我先澄清一个概念,那就是“复杂网络
  • ML之RL:强化学习Reinforcement Learning的简介、应用、经典案例、学习资源之详细攻略 目录 强化学习的简介 0、强化学习相关论文 1、强化学习的常用算法 1.1、策略学习 1.2、Q-Learning 2、强化学习...
  • 人工智能工程师学习路线及具备的5项基本技能

    万次阅读 多人点赞 2016-09-08 23:55:42
    对机器学习工程师而言,计算机科学基础的重要性包括数据结构(数据堆栈、队列、多位数组、树形以及图像等等)、算法(搜索、分类、优化、动态编程等)、科计算性与复杂性(P对NP、NP完全问题、大O符号以及近似算法等)和...
  • MATLAB的一些功能和案例

    千次阅读 2019-03-10 16:30:18
    mathematica 可能是数学界最好的狙击枪 ...MATLAB拥有丰富的算法工具箱,因此在工程计算、控制设计、信号处理与通讯、图像处理、信号检测、金融建模设计与分析等领域都能看到它的身影,可谓是无处不在。 ...
  • 大型网站技术架构:核心原理与案例分析 (最接地气的网站架构经验,网站生存技术心要,应对大数据挑战的干货分享!) 李智慧 著 ISBN 978-7-121-21200-0 2013年9月出版 定价:59.00元 240页 16开 编辑推荐 ...

空空如也

空空如也

1 2 3 4 5 ... 20
收藏数 42,382
精华内容 16,952
关键字:

复杂工程问题的具体案例