Stata数据处理:xtbalance-非平衡面板之转换

发布时间:2020-10-07 阅读 24

Stata 连享会   主页 || 视频 || 推文

温馨提示: 定期 清理浏览器缓存,可以获得最佳浏览体验。

课程详情 https://gitee.com/arlionn/Course   |   lianxh.cn

课程主页 https://gitee.com/arlionn/Course

作者:吴雄 (湘潭大学)


目录


重要声明 (2019.4.16-连玉君):
在实证分析过程中,使用平行面板数据通常是不得已而为之的事情。这是因为,受限于计量理论的发展,有些模型只能应用于平行面板,如 Hansen (1999, JoE) 提出的面板门槛模型;Love and Zicchino (2006, QREF) 文中使用的面板 VAR 模型。事实上,强行把数据处理为平行面板数据,意味着留下来的公司都是上市时间较长、规模较大的公司,基于这些公司得到的结论并不能直接推广到所有公司中。简言之,使用平行面板数据存在一个潜在的风险:我们在数据处理过程中,人为地引入了样本选择偏误问题。因此,如果你使用的模型适用于非平行面板,那么要把尽可能完整的数据纳入样本,而尽力避免人为删减。

  • Hansen, B., 1999, Threshold effects in non-dynamic panels: Estimation, testing, and inference, Journal of Econometrics, 93 (2): 345-368. -PDF-
  • Love, I., L. Zicchino, 2006, Financial development and dynamic investment behavior: Evidence from panel VAR, Quarterly Review of Economics and Finance, 46 (2): 190-210. -Link-

之前,我在处理数据的时候,经常碰到一些非平衡面板数据,当时处理完后才发现连玉君老师之前已经编写了一个 xtbalance 的命令,该命令专门用于将连续时间非平衡面板处理成平衡面板。但是,该命令在处理非连续时间的非平衡面板有点缺陷,所以平时我还是自己写命令来处理非平衡面板数据的问题,这两天我发现有同学还有一些别的交流群里的群友在用的时候就碰到这个问题,今天,我就打算细讲如何将非平衡面板转换成平衡面板。

1. xtbalance 命令的使用

首先,这个命令是 Stata 外部命令,需要先下载安装才能使用。下载安装的命令为: ssc install xtbalance。完成后,输入 help xtbalance 查看帮助文档,以了解该命令的使用方法。

xtbalance 的语法格式: xtbalance, range(numlist) [ miss(varlist) ]

  • 请注意,在使用该命令之前你需要设置你的面板数据,你可以通过 xtset panelvar timevartsset panelvar timevar 将数据设定成面板数据格式。

接下来,你可以根据所需时间段来处理数据,比如我需要 1992-1998 年的平行面板,命令为 xtbalance, range(1992 1998)

  • 局限:当你的 timevar 不是 1991、1992、……2000 这样的连续时间,而是类似 1992、1994、1996 …… 2000 这种非连续时间的时,直接使用 xtbalance, range(1992 1998) 会导致所有观察值都被删除了。的结果将会删除你的整个样本,这是怎么回事呢?
  • 当我对我的非连续时间的平衡面板 1992(2)2000 ,进行上述命令的时候,出来的结果如下:
//数据生成
. set obs 100
. gen id = int(_n/5.001)+1
. bysort id:gen year = 1992 +2*(_n-1)
. xtset id year

       panel variable:  id (strongly balanced)
        time variable:  year, 1992 to 2000, but with gaps
                delta:  1 unit

//取1992-1998年段的平衡面板
. xtbalance, range(1992 1998)

(20 observations deleted due to out of range) 
(80 observations deleted due to discontinues) 

即,该命令首先将不在你选定的时间段内的样本删掉,之后,它在清理每个 id 的时候,将组内非连续时间的 id 删掉,但为什么我的平衡面板会被全部删除呢?因为我的不是连续时间。那么连续是怎么计算的呢?我的猜测是这个命令按照连续时间来计算每个 id 的样本数量,将其样本数量与预计间隔相比较,即它在清理每个 id 的时候,将组内没有 1998 - 1992 + 1 数量的id删掉,但是我们的时间间隔不一样,每个组内的样本数是不一样的,我的每个 id 应该只有 ( 1998 - 1992 ) / 2 +1个,它按照连续时间来计算的话会比我多,所以它认为我的组内缺失了样本,不是平衡的,所以会将这些也删掉。结果,数据就全被删了。

2. xtbalance 的流程

我们这里就不贴xtbalance命令的源代码,但是我通过自己编写的一个do文件来展示我猜测的具体操作流程。

2.1 生成连续时间的非平衡面板

我们首先生成一个 id 为 0 (1) 99,year 为 1991 (1) 2000 的平衡面板:

. clear
. set  obs 1000
. gen id =int(_n/10.000001)
. bysort id :gen  year = 1990 + _n
. xtset id year

       panel variable:  id (strongly balanced)
        time variable:  year, 1991 to 2000
                delta:  1 unit

然后,我们生成均匀分布的随机数,将随机数小于 0.2 的样本删掉,即每条都有 20% 的概率被删掉,剩下的样本为非平衡的样本

. drop if runiform() <0.2
. xtset id year

       panel variable:  id (unbalanced)
        time variable:  year, 1991 to 2000, but with gaps
                delta:  1 unit

同时,通过tab id我们可以看每个id的样本数(受限于编辑器,这里只列出几行)都不一样

. tab id 

         id |      Freq.     Percent        Cum.
------------+-----------------------------------
          0 |          6        0.73        0.73
          1 |          9        1.10        1.83
          2 |          8        0.98        2.81
          3 |          9        1.10        3.91
          4 |          7        0.86        4.77
          5 |          9        1.10        5.87

  • 注意:这时候,如果在1991(1)2000时间段上是平衡面板的话,每个id应该有2000-1991+1=10条记录

连享会计量方法专题……

2.2 不用 xtbalance 命令的处理成平衡面板的方法

实际上,xtbalance 命令的实现是这样的:

删除不在时间段内的样本;
计算每个id的样本数,如果每个 id 组内缺少样本,则将这个 id 的样本都删除。

假如,我们需要将上述数据 id : 0 (1) 99 year: 1991 (1) 2000的非平衡面板转为 id :0 (1) 99 year: 1992 (1) 1998的平衡面板的话,我们需要知道当转为平衡面板后,每个id相对应的只有1998-1992+1=7条记录

. preserve
. drop if year > 1998 | year < 1992
(243 observations deleted)

. bysort id :keep if _N ==7
(400 observations deleted)

. xtset id year
       panel variable:  id (strongly balanced)
        time variable:  year, 1992 to 1998
                delta:  1 unit
. restore

2.3 xtbalance 的使用

. xtbalance, range(1992 1998)

(243 observations deleted due to out of range) 
(400 observations deleted due to discontinues) 

. xtset id year
       panel variable:  id (strongly balanced)
        time variable:  year, 1992 to 1998
                delta:  1 unit

3. 非连续时间的非平衡面板的处理

  • 本节将介绍有固定间隔时间的非平衡面板的处理

实际过程中,有许多数据库并不是连续时间的面板,这可能是因为多种原因,比如,某个数据库在调查数据时候,分别在 1990、1992、1994 每两年调查一次的,其实,这种满好的,因为有固定间隔,然而,当不是固定间隔的时候,处理数据的时候你可能需要多留意。

3.1 生成数据

先生成平衡面板(不是连续时间)

  • obs : 1000
  • id :1 (1) 99
  • year:1991 (2) 2009
*-生成非连续时间的平衡面板
. clear
. set obs 1000
. gen id =int(_n/10.000001)
. bysort id :gen  year = 1990 + 2*_n -1
. xtset id year
       panel variable:  id (strongly balanced)
        time variable:  year, 1991 to 2009, but with gaps
                delta:  1 unit

. xtset id year, delta(2)
       panel variable:  id (strongly balanced)
        time variable:  year, 1991 to 2009
                delta:  2 units

. tab year

       year |      Freq.     Percent        Cum.
------------+-----------------------------------
       1991 |        100       10.00       10.00
       1993 |        100       10.00       20.00
       1995 |        100       10.00       30.00
       1997 |        100       10.00       40.00
       1999 |        100       10.00       50.00
       2001 |        100       10.00       60.00
       2003 |        100       10.00       70.00
       2005 |        100       10.00       80.00
       2007 |        100       10.00       90.00
       2009 |        100       10.00      100.00
------------+-----------------------------------
      Total |      1,000      100.00
*-直接使用xtbalance的缺陷/
. preserve

. count 
  1,000

. xtbalance, range(1993 2005)

(300 observations deleted due to out of range) 
(700 observations deleted due to discontinues) 

. count 
  0
 
. restore

注意:

  1. xtset id yeartsset id year 都可以同时设置面板
  2. 因为是非连续时间的平衡面板 ,所以 xtset id year 命令会提示说你的数据 “strongly balanced" 但是时间有 "gap",如果你的面板 time variable 是有固定间隔的,那么你可以在 xtset id year, delta()delta() 选项中设置。
  3. 通过上述 xtbalance 命令,我们可以看到,我们的非连续时间的平衡面板直接使用用xtbalance 是不合适的。

再通过随机删除部分样本,使其成为非平衡面板:

. drop if runiform() <0.2
(168 observations deleted)

. xtset id year,delta(2)
       panel variable:  id (unbalanced)
        time variable:  year, 1991 to 2009, but with gaps
                delta:  2 units

3.2 处理成平衡面板

我们所需要的样本时间段为 1993(2)2005: 先查看一下数据:

. tab year

       year |      Freq.     Percent        Cum.
------------+-----------------------------------
       1991 |         78        9.38        9.38
       1993 |         84       10.10       19.47
       1995 |         80        9.62       29.09
       1997 |         82        9.86       38.94
       1999 |         82        9.86       48.80
       2001 |         88       10.58       59.38
       2003 |         79        9.50       68.87
       2005 |         86       10.34       79.21
       2007 |         87       10.46       89.66
       2009 |         86       10.34      100.00
------------+-----------------------------------
      Total |        832      100.00

我们所需要的是 1993(2)2005 的时间段的话,每个 id 在 1993(2)2005时间段内的样本数应该是1+(2005-1993)/2 = 7,所以,我们的操作流程就是: 1.先只保留1993-2005年的所有样本,不在时间段内的删除掉; 2.计算每个id的样本数,只包括样本数为7的。

. preserve

. drop if year>2005 | year <1993
(251 observations deleted)

. bysort id :drop if _N != 7
(413 observations deleted)

. xtset id year,delta(2)
       panel variable:  id (strongly balanced)
        time variable:  year, 1993 to 2005
                delta:  2 units

. restore

3.3 使用 xtbalance 的新姿势

对于有固定间隔的平衡面板数据,我们可以预先生成一个新的时间变量 (连续的),进而使用 xtbalance 命令进行处理。

. xtset id year, delta(2)
       panel variable:  id (unbalanced)
        time variable:  year, 1991 to 2009, but with gaps
                delta:  2 units

. bysort id: gen new_year = _n  //使用该命令前一点要先对数据排序
* 或 gen new_year = 1 + (year - r(min))/2

现在 1993 年在 new_year 中就是 2,而 2005 年就是 8 ,然后用新的时间来设置面板,再使用xtbalance,range(2 8) 就OK了

 . xtset id new_year
       panel variable:  id (unbalanced)
        time variable:  new_year, 1 to 10, but with gaps
                delta:  1 unit

. xtbalance,range(2 8)

(251 observations deleted due to out of range) 
(413 observations deleted due to discontinues) 

. xtset id year,delta(2)
       panel variable:  id (strongly balanced)
        time variable:  year, 1993 to 2005
                delta:  2 units

连享会计量方法专题……

4. 非平衡面板非连续时间也没有固定间隔

股票日交易资料有一个典型的特征:所有公司的资料在非交易日都是缺失的。因此,虽然股票日交易资料本质上是一份连续数据,但 Stata 在接到 xtset id date 的通知后,将其视为非平衡面板数据。(Note: 这里暂不考虑那些在交易日里停牌的公司)

此时的处理方法与上一小节相似:可以先使用 bysort id: gen new_data=_n 命令或 egen new_date = group(date) 命令生成新的时间变量。

对于更为一般的情形,处理方法也会相对复杂:先删掉不在时间段内的样本,然后通过某种方法将你的时间变量转为一个新的具有连续时间的变量,之后通过每个 id 的样本数与为平衡时的样本数进行比较,一样则保留,否则删除。

5. 后记 (连玉君)

在写作这篇推文过程中,我与吴雄多次沟通,受到了不少启发。

后续我们会将文中提及的 xtbalance 的局限一一解决掉,以便大家能够更为便捷地进行非平行面板 → 平行面板的转换。

计划添加的功能如下(欢迎各位补充,反馈至:arlionn@163.com ):

  • 添加 delta() 选项:以便处理有固定间隔的平衡面板数据
  • 添加 gen(newvarname) 选项:以便对平行面板构成的观察值进行标记;
  • 添加 force 选项:由程序自动对用户的数据进行处理;
  • ……

上述想法促成了展金永等三位同学编写了 tobalance 命令,可以处理更为一般化的情形,详见 Stata新命令-tobalance:非平行面板转换为平行面板数据


相关课程

连享会-直播课 上线了!
http://lianxh.duanshu.com

免费公开课:


课程一览

支持回看,所有课程可以随时购买观看。

专题 嘉宾 直播/回看视频
最新专题 DSGE, 因果推断, 空间计量等
Stata数据清洗 游万海 直播, 2 小时,已上线
研究设计 连玉君 我的特斯拉-实证研究设计-幻灯片-
面板模型 连玉君 动态面板模型-幻灯片-
面板模型 连玉君 直击面板数据模型 [免费公开课,2小时]

Note: 部分课程的资料,PPT 等可以前往 连享会-直播课 主页查看,下载。


关于我们

  • Stata连享会 由中山大学连玉君老师团队创办,定期分享实证分析经验。直播间 有很多视频课程,可以随时观看。
  • 连享会-主页知乎专栏,300+ 推文,实证分析不再抓狂。
  • 公众号推文分类: 计量专题 | 分类推文 | 资源工具。推文分成 内生性 | 空间计量 | 时序面板 | 结果输出 | 交乘调节 五类,主流方法介绍一目了然:DID, RDD, IV, GMM, FE, Probit 等。
  • 公众号关键词搜索/回复 功能已经上线。大家可以在公众号左下角点击键盘图标,输入简要关键词,以便快速呈现历史推文,获取工具软件和数据下载。常见关键词:课程, 直播, 视频, 客服, 模型设定, 研究设计, stata, plus, 绘图, 编程, 面板, 论文重现, 可视化, RDD, DID, PSM, 合成控制法

连享会主页  lianxh.cn
连享会主页 lianxh.cn

连享会小程序:扫一扫,看推文,看视频……

扫码加入连享会微信群,提问交流更方便

✏ 连享会学习群-常见问题解答汇总:
https://gitee.com/arlionn/WD