以非字母数字顺序对字符串变量进行编码

时间:2013-12-05 15:43:46

标签: label encode stata

我希望encode一个字符串变量,使得分配的数字代码遵循字符串值的原始顺序(如使用browse时所示)。为什么?在使用reshape wide时,我需要编码的变量标签来获取正确的变量名称。

假设var是一个没有标签的字符串变量:

var      label(var)  
"zoo"    none  
"abc"    none

如果您从:

开头
  

编码var,gen(var2)

标签是1 =“abc”2 =“zoo”,可以看到

  

标签li

但我希望标签按照它们的顺序进行排序,如browse所示,以便稍后变更的变量顺序。

我没有找到encode选项,其中按照我在使用browse时看到的顺序添加标签。

我最好的想法是手工完成:

  

ssc install labutil
  labvalch var,f(1 2)t(2 1)

这很好,但我有> 50个列表条目。

其他方法:使用reshape时使用其他订单,但我认为不起作用。

  

重塑宽x,i(id)j(var)

我只找到了

  

ssc install labutil
  labmask区域代码,值(区域)

作为encode的替代选项,但我无法使用labmask处理字符串。

3 个答案:

答案 0 :(得分:3)

首先,在Stata中,字符串变量不能包含值标签。只有数字变量才能有值标签。实质上,您想要的值标签已经在您的字符串变量中作为字符串值。因此,问题的核心是您需要使用正确顺序的值创建数值变量。

让我们以最简单的形式解决问题:字符串值只出现一次和一次。所以

gen long order = _n 
labmask order, values(var) 

然后解决问题,因为数值1,2,...与字符串值zooabc,无论如何,它们成为值标签。顺便提一下,我的一个labmask的更好的参考是 http://www.stata-journal.com/sjpdf.html?articlenum=gr0034

现在让它变得更复杂。字符串值可能会出现一次或多次,但我们希望数值变量在数据中首先出现。

gen long order1 = _n
egen order2 = min(order1), by(var) 
egen order = group(order2) 
labmask order, values(var) 

这是如何工作的。

gen long order1 = _n 

将观察数字1,2放在一个新变量中。

egen order2 = min(order1), by(var)

找到var的每个不同值的第一个匹配项。

egen order = group(order2) 

将这些数字映射到1,2,无论如何。

labmask order, values(var)

order的数字值与var的字符串值相关联,后者将成为其值标签。

这是一个在实践中如何运作的例子。

. l, sep(0)

    +---------------------------------+
    |   var   order1   order2   order |
    |---------------------------------|
 1. |   zoo        1        1     zoo |
 2. |   abc        2        2     abc |
 3. |   zoo        3        1     zoo |
 4. |   abc        4        2     abc |
 5. |   new        5        5     new |
 6. | newer        6        6   newer |
    +---------------------------------+

. l, nola sep(0)

    +---------------------------------+
    |   var   order1   order2   order |
    |---------------------------------|
 1. |   zoo        1        1       1 |
 2. |   abc        2        2       2 |
 3. |   zoo        3        1       1 |
 4. |   abc        4        2       2 |
 5. |   new        5        5       3 |
 6. | newer        6        6       4 |
    +---------------------------------+

一旦得到了正确答案,你就会drop order1 order2

另请参阅sencode以获取其他解决方案。 (search sencode查找引用和下载位置。)

答案 1 :(得分:3)

Roger Newson编写的用户编写的命令sencode(超级编码),可用的ssc describe sencode可用于您想要的内容。不是根据字符串变量的字母数字顺序分配数字代码,而是可以使用值在原始数据集中出现的顺序进行分配。

clear all
set more off

*------- example data ---------

input str10 var
abc
zoo
zoo
zoo
elephant
elephant
abc
abc
elephant
zoo
end

*------- encode ---------------

encode var, generate(var2)
sencode var, generate(var3)

list, separator(0)
list, separator(0) nolabel

变量var3是所需的形式。与var2对比。

答案 2 :(得分:1)

我不确定是否有一个优雅的解决方案,因为我认为levelsof按字母顺序排列字符串。

只要您的列表是唯一的,这应该有效。

clear
input str3 myVar 
"zoo"
"abc"
"def"
end

* for reshape
generate iVar = 1
generate jVar = _n

* reshape to wide
reshape wide myVar, i(iVar) j(jVar)
list

* create label
local i = 0
foreach v of varlist myVar* {
    local ++i
    local myVarName = `v'
    label define myLabel `i' "`myVarName'", add
}

* reshape to wide
reshape long myVar, i(iVar) j(myVarEncoded)

* assign label
label value myVarEncoded myLabel