如何使用SAS计算Word Mover的距离

Word Mover的距离(WMD)是用于衡量两个文档之间差异的距离度量,它在文本分析中的应用是由华盛顿大学的一个研究小组在2015年引入的。该小组的论文“ 从Word嵌入到文档距离”发表了在第32届国际机器学习大会(ICML)上。在本文中,他们证明了WMD度量导致8个真实世界文档分类数据集中前所未有的低k-最近邻文档分类错误率。

他们利用单词嵌入和WMD对文档进行分类,这种方法相对于传统方法的最大优点是它能够将单个单词对(例如总统和奥巴马)之间的语义相似性合并到文档距离度量中。以传统方式,操纵语义相似单词的一种方法是提供同义词表,以便算法在测量文档距离之前可以将具有相同含义的单词合并到代表性单词中,否则您将无法获得准确的相异性结果。然而,维护同义词表需要人类专家的不断努力,因此耗时且非常昂贵。此外,单词的语义含义取决于域,而通用同义词表不适用于不同的域。

Word Mover距离的定义

WMD是两个文档之间的距离,作为将所有单词从一个文档移动到另一个文档所需的最小(加权)累积成本。通过解决以下线性程序问题来计算距离。

T ij表示文档d中的单词i在文档d ‘中移动到单词j的多少;

c(i; j)表示从文件d中的单词i到文件d ‘中的单词j“行进”的费用; 这里的成本是word2vec嵌入空间中的两个词‘欧几里德距离;

如果字我出现? 我在文档d次,我们记

WMD是地球移动器距离度量(EMD)的一个特例,这是一个众所周知的运输问题。

如何用SAS计算地球移动器的距离?

SAS / OR是解决运输问题的工具。图1显示了一个带有四个节点和节点之间距离的传输示例,我从这个Earth Mover的Distance文档中复制了这些节点。目标是找出从{x1,x2}到{y1,y2}的最小流量。现在让我们看看如何使用SAS / OR解决这个运输问题。

节点的权重和节点之间的距离如下。

图-1运输问题

datax_set;input_node_ $ _sd_;datalines;x10.74x20.26;datay_set;input_node_ $ _sd_;datalines;y10.23y20.51;dataarcdata;input_tail_ $ _head_ $ _cost_;datalines;x1 y1155.7x1 y2252.3x2 y1292.9x2 y2198.2;proc optmodel;setxNODES;num w{xNODES};setyNODES;num u{yNODES};set<str,str> ARCS;num arcCost{ARCS}; readdatax_setintoxNODES=[_node_]w=_sd_;readdatay_setintoyNODES=[_node_]u=_sd_;readdataarcdataintoARCS=[_tail_ _head_]arcCost=_cost_;varflow{<i,j>inARCS}>=0;impvar sumY =sum{jinyNODES}u[j];minobj =(sum{<i,j>inARCS}arcCost[i,j]* flow[i,j])/sumY;con con_y{jinyNODES}:sum{<i,(j)>inARCS}flow[i,j]= u[j];con con_x{iinxNODES}:sum{<(i),j>inARCS}flow[i,j]<= w[i]; solve with lp / algorithm=ns scale=none logfreq=1;print flow;quit;

<str,str>

<str,str>SAS / OR的解决方案如表-1所示,EMD是目标值:203.26756757。

表-1 EMD用SAS / OR计算

我用SAS / OR表2得到的流量数据显示如下,与上述地球移动器距离文档中公布的图表相同。

表-2 SAS / OR的流量数据

图-2运输问题流程图

如何用SAS计算Word Mover的距离

本文从Word嵌入到文档距离,通过删除WMD的第二个约束来减少计算,提出了一个名为Relaxed Word Mover Distance(RWMD)的新度量。由于我们需要读取文字嵌入数据,因此我将向您展示如何使用SAS Viya计算两个文档的RWMD。

/* start CAS server */cas casauto host="host.example.com"port=5570;libnamesascas1 cas;/* load documents into CAS */datasascas1.documents;infiledatalines delimiter=‘|‘missover;lengthtext varchar(300);inputtext$ did;datalines;Obama speaks to the mediainIllinois.|1The President greets the pressinChicago.|2;run;/* create stop list*/datasascas1.stopList;infiledatalines missover;lengthterm $20;inputterm$;datalines;thetoin;run;/* load word embedding model */proc cas;loadtable path=‘datasources/glove_100d_tab_clean.txt‘caslib="CASTestTmp"importOptions={fileType="delimited",delimiter=‘\t‘,getNames=True,guessRows=2.0,varChars=True}casOut={name=‘glove‘replace=True};run;quit;%macrocalculateRWMD(textDS=documents,documentID=did,text=text,language=English,stopList=stopList,word2VectDS=glove,doc1_id=1,doc2_id=2);/* text parsing and aggregation */proc cas;textParse.tpParse/table={name="&textDS",where="&documentID=&doc1_id or &documentID=&doc2_id"}docId="&documentID",language="&language",stemming=False,nounGroups=False,tagging=False,offset={name="outpos",replace=1},text="&text";run; textparse.tpaccumulate/parent={name="outparent1",replace=1}language="&language",offset=‘outpos‘,stopList={name="&stoplist"},terms={name="outterms1",replace=1},child={name="outchild1",replace=1},reduce=1,cellweight=‘none‘,termWeight=‘none‘;run;quit;/* terms of the two test documents */proc cas;loadactionset"fedsql";execdirect casout={name="doc_terms",replace=true}query="

select outparent1.*,_term_

from outparent1

left join outterms1

on outparent1._termnum_ = outterms1._termnum_

where _Document_=&doc1_id or _Document_=&doc2_id;

";run;quit;/* term vectors and counts of the two test documents */proc cas;loadactionset"fedsql";execdirect casout={name="doc1_termvects",replace=true}query="

select word2vect.*

from &word2VectDS word2vect, doc_terms

where _Document_=&doc2_id and lowcase(term) = _term_;

";run; execdirect casout={name="doc1_terms",replace=true}query="

select doc_terms.*

from &word2VectDS, doc_terms

where _Document_=&doc2_id and lowcase(term) = _term_;

";run; simple.groupBy /table={name="doc1_terms"}inputs={"_Term_","_Count_"}aggregator="n"casout={name="doc1_termcount",replace=true};run;quit;proc cas;loadactionset"fedsql";execdirect casout={name="doc2_termvects",replace=true}query="

select word2vect.*

from &word2VectDS word2vect, doc_terms

where _Document_=&doc1_id and lowcase(term) = _term_;

";run; execdirect casout={name="doc2_terms",replace=true}query="

select doc_terms.*

from &word2VectDS, doc_terms

where _Document_=&doc1_id and lowcase(term) = _term_;

";run; simple.groupBy /table={name="doc2_terms"}inputs={"_Term_","_Count_"}aggregator="n"casout={name="doc2_termcount",replace=true};run;quit;/* calculate Euclidean distance between words */datadoc1_termvects;setsascas1.doc1_termvects;run;datadoc2_termvects;setsascas1.doc2_termvects;run;proc iml;use doc1_termvects;read allvar_char_intolterm;read allvar_num_intox;closedoc1_termvects; use doc2_termvects;read allvar_char_intorterm;read allvar_num_intoy;closedoc2_termvects; d = distance(x,y); lobs=nrow(lterm);robs=nrow(rterm);d_out=j(lobs*robs, 3, ‘ ‘);doi=1to lobs;doj=1to robs;d_out[(i-1)*robs+j,1]=lterm[i];d_out[(i-1)*robs+j,2]=rterm[j];d_out[(i-1)*robs+j,3]=cats(d[i,j]);end;end;createdistancefromd_out;appendfromd_out;closedistance;run;quit;/* calculate RWMD between documents */datax_set;setsascas1.doc1_termcount;rename_term_=_node_;_weight_=_count_;run;datay_set;setsascas1.doc2_termcount;rename_term_=_node_;_weight_=_count_;run;dataarcdata;setdistance;renamecol1=_tail_;renamecol2=_head_;length_cost_8;_cost_= col3;run;proc optmodel;setxNODES;num w{xNODES};setyNODES;num u{yNODES};set<str,str> ARCS;num arcCost{ARCS}; readdatax_setintoxNODES=[_node_]w=_weight_;readdatay_setintoyNODES=[_node_]u=_weight_;readdataarcdataintoARCS=[_tail_ _head_]arcCost=_cost_;varflow{<i,j>inARCS}>=0;impvar sumY =sum{jinyNODES}u[j];minobj =(sum{<i,j>inARCS}arcCost[i,j]* flow[i,j])/sumY;con con_y{jinyNODES}:sum{<i,(j)>inARCS}flow[i,j]= u[j];/* con con_x {i in xNODES}: sum {<(i),j> in ARCS} flow[i,j] <= w[i];*/solve with lp / algorithm=ns scale=none logfreq=1;callsymput(‘obj‘, strip(put(obj,best.)));createdataflowDatafrom[i j]={<i, j="">inARCS: flow[i,j].sol >0}col("cost")=arcCost[i,j]col("flowweight")=flow[i,j].sol;run;quit;%putRWMD=&obj;%mendcalculateRWMD; %calculateRWMD(textDS=documents,documentID=did,text=text,language=English,stopList=stopList,word2VectDS=glove,doc1_id=1,doc2_id=2);

<str,str>

<str,str>proc printdata=flowdata;run;quit;

WMD方法不仅可以测量文档的相似性,还可以通过可视化流数据来解释为什么这两个文档是相似的。

原文地址:https://www.cnblogs.com/tecdat/p/9317446.html

时间: 2024-10-13 08:53:32

如何使用SAS计算Word Mover的距离的相关文章

计算两点间的距离

计算两点间的距离 Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 65536/32768 K (Java/Others)Total Submission(s): 208295    Accepted Submission(s): 72641 Problem Description 输入两点坐标(X1,Y1),(X2,Y2),计算并输出两点间的距离. Input 输入数据有多组,每组占一行,由4个实数组成,分别表示x1,y1,x2,y

利用结构类型的相关知识计算两点之间的距离

#include<stdio.h>#include<stdlib.h>#include<math.h> struct point{ /*点的结构类型名*/ float x; /*横坐标*/ float y; /*纵坐标*/ }; struct point readPoint(); /*函数原型声明*/float distance(struct point p1,struct point p2);/*主函数*/ int main(void){ struct point a

2D和3D空间中计算两点之间的距离

自己在做游戏的忘记了Unity帮我们提供计算两点之间的距离,在百度搜索了下. 原来有一个公式自己就写了一个方法O(∩_∩)O~,到僵尸到达某一个点之后就向另一个奔跑过去 /// <summary> /// 3维中如何计算两点之间的距离 /// </summary> /// <param name="p1"></param> /// <param name="p2"></param> /// &l

HDOJ 2001 计算两点间的距离

计算两点间的距离 Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 65536/32768 K (Java/Others) Total Submission(s): 94573    Accepted Submission(s): 36296 Problem Description 输入两点坐标(X1,Y1),(X2,Y2),计算并输出两点间的距离. Input 输入数据有多组,每组占一行,由4个实数组成,分别表示x1,y1,x2,y

Distributed Sentence Similarity Base on Word Mover&#39;s Distance

Algorithm: Refrence from one ICML15 paper: Word Mover's Distance. 1. First use Google's word2vec tool to get distributed word representing aka. word vectors. 2. Then use earth mover's distance as similarity measure metric. 3. Solve the EMD problem as

ios根据gps坐标来计算两点间的距离

//ios根据gps坐标来计算两点间的距离 //x1,y1 点1的坐标 x2,y2点2的坐标 -(double) gps2m:(double)x1 _y1:(double)y1 _x2:(double)x2 _y2:(double)y2{ double radLat1 = (x1 * 3.1416 / 180.0); double radLat2 = (x2 * 3.1416 / 180.0); double a = radLat1 - radLat2; double b = (y1 - y2)

C++刷题——1924: 计算两点间的距离

1924: 计算两点间的距离 Description 输入两点坐标(X1,Y1),(X2,Y2),计算并输出两点间的距离. Input 输入数据有多组,每组占一行,由4个实数组成,分别表示x1,y1,x2,y2,数据之间用空格隔开. Output 对于每组输入数据,输出一行,结果保留两位小数. /* Copyright (c) 2014, 烟台大学计算机学院 * All rights reserved. * 文件名称:test.cpp * 作者:陈丹妮 * 完成日期:2015年 5 月 20 日

计算两点间的距离,hdu-2001

计算两点间的距离 Problem Description 输入两点坐标(X1,Y1),(X2,Y2),计算并输出两点间的距离. Input 输入数据有多组,每组占一行,由4个实数组成,分别表示x1,y1,x2,y2,数据之间用空格隔开. Output 对于每组输入数据,输出一行,结果保留两位小数. Sample Input 0 0 0 1 0 1 1 0 Sample Output 1.00 1.41 1 #include<stdio.h> 2 #include<stdlib.h>

计算纬度、经度距离,返回公里(千米)数

using System;using System.Collections.Generic;using System.Linq;using System.Text;using System.Threading.Tasks; namespace ClDing.Utility{ /// <summary> /// 计算纬度.经度距离 /// </summary> public class Distance { private const double EARTH_RADIUS = 63