SAS笔记(1) PDV与数据读入
其实我是不喜欢SAS的。当然,我不喜欢她,并不代表她不好,实际上在某些应用场景下SAS是款很优秀的软件。我的数据分析之路始于R,品尝过R的灵活与简洁(不论是软件安装还是语法)后,再来学习SAS,的确提不起兴致。然而由于:1.导师的项目数据量较大(几Gb到几十Gb);2.之前的项目代码师兄已经用SAS很优美地实现了;3.我莫名地当上了该项目负责人,要带着师弟师妹做该项目。我也只好硬着头皮学习SAS。奈何现在脑力大不如前,看的东西越来越记不住,于是下定决心梳理一下SAS相关知识。
1. DATA步简介
在SAS中,我们使用DATA步来读入数据,DATA步在读入数据时实际上有两个阶段:编译(compilation)和执行(execution)。过程如下:
- 在编译阶段中,逐个扫描语句,如果发现语法错误,SAS报错并终止运行;如果编译阶段中没有发现任何语法错误,进入执行阶段。
- 在执行过程中,DATA部读入第一条数据,在SAS中创建第一条观测;读入第二条数据,在SAS中创建第二条观测;读入第三条数据,在SAS中创建第三条观测……直至读入最后一条数据并在SAS中创建最后一条观测。我们可以把这个过程当做隐式循环(和DO,DO WHILE,DO UNTIL语句区分,它们是显示循环)。
需要注意的是,并不是DATA步中的所有语句都是在执行阶段运行,事实上,可以把DATA步语句分为两类:可执行语句(executable)和声明语句(declarative)。
声明语句只在编译阶段起作用,它可以放在DATA步的任何位置。下面是一些基本的DATA步声明语句:
LENGTH:设置内部变量长度
FORMAT:设置变量输出格式
LABEL:设置变量标签
DROP:指示输出文件中删掉哪些变量
KEEP:指示输出文件中包含哪些变量
与声明语句不同,可执行语句在DATA步中顺序很重要。比如从外部读取一个文本文件,我们必须以INFILE语句开始,告诉SAS从哪里读文件;然后输入INPUT语句,告诉SAS怎么读该文件。所以,INFILE语句必须在INPUT语句前面,顺序很重要。
2. DATA步的编译阶段(DATA Step Compilation Phase)
SAS从外部读入原始数据(raw data)时,会在编译阶段开始时创建一个输入缓冲区(input buffer)来存储raw data。如果是从外部直接读入SAS数据(.sas7bdat文件)则不会创建输入缓冲区。SAS在编译阶段还会创建PDV(program data vector),PDV其实就是内存中的一块区域,通过PDV将读入的raw data的每一条数据变成SAS数据集中的每一条观测。在PDV中有两个自动变量,_N_和_ERROR_。_N_=1表示正在创建第一条观测,_N_=2表示正在创建第二条观测,依次类推。_ERROR_只有0和1两个取值,等于0表示在创建当前观测时未发现错误,等于1表示在创建当前观测时发现错误。除了这两个自动变量外,PDV中还有DATA步在创建的数据变量。
假设在我们电脑D盘里有一个student.txt文件,内容如下(第一行红字表示每个字符的所占列位置编号,不是文档内容)
Barbara 61 12D
John 62 175
现在我们用DATA步读入这个文件,并计算每个学生的BMI,看看PDV的工作原理。代码很简单:
data ex1;
infile 'C:\student.txt';
input name $ 1-7 height 9-10 weight 12-14;
BMI = 700*weight/(height*height);
output;
run;
- 一开始,PDV中只有_N_,_ERROR_这两个自动变量。
- 代码运行到 input name $ 1-7 height 9-10 weight 12-14;时,PDV中会按照input后变量的顺序创建NAME,HEIGHT,WEIGHT三个变量,D表示dropped,K表示kept。只有带K的变量才会output到数据集中。
- 代码运行到BMI = 700*weight/(height*height);时,PDV中创建BMI这个变量
在编译阶段,SAS会检查语法是否正确,在编译结束的时候,会创建SAS数据集的内容描述,包括数据集的名字,观测数,变量名,变量数目,变量类型,所有这些内容都可以通过CONTENTS输出。
3. DATA步的执行阶段(DATA Step Execution Phase)
- 在执行阶段的开始,自动变量_N_会被初始化1,自动变量_ERROR_被初始化0。一旦INFILE语句识别了我们待读取文件的路径,INPUT语句就会把待读取文件的第一条数据复制到输入缓冲区。
- 接着,我们的输入指针(input pointer,下图的红色箭头)会在(@)输入缓冲区的开始处。
- 然后,输入指针(红色箭头)会根据input语句定义的方式读入输入缓冲区的这条记录,并移动输入指针,在我们的例子中是将1-7列读入NAME,9-10列读入HEIGHT,12-14列读入WEIGHT,此时输入指针位于第15列。将记录写入到PDV,因为WEIGHT变量类型错误,所以WEIGHT变量值为空(.),同时_ERROR_会变为1,因为WEIGHT为空,所以BMI也为空。
- 然后执行OUTPUT语句,将PDV中的这条数据输出到我们的SAS数据集--WORK逻辑库中的ex1。到此student.txt中的第一条数据已读入SAS数据集。
- SAS返回到DATA步的第一条语句,也就是data ex1;开始读取student.txt中的第二条数据,此时_N_变为2,_ERROR_重新置为0,其余过程同上。如此往复,直至我们的输入指针遇到EOF(End Of the File),退出循环。DATA步结束。
在我们的这个例子中,如果我们不使用OUTPUT也可以读入该数据,这是因为在DATA步中,当用户没有显式指定OUTPUT时,SAS会隐式调用OUTPUT。不论显式还是隐式output,它们的作用都是讲PDV的那条数据output到我们的SAS数据集中。
参考资料:《Handbook of SAS® DATA Step Programming》
SAS笔记(1) PDV与数据读入的更多相关文章
- Keras学习笔记一:修改数据读入方式为本地图片读入
第一种方法: Keras官方给的图片去噪示例要自动下载mnist数据集并处理,不能修改和加入自己的数据集. from keras.datasets import mnist (x_train, _), ...
- R学习笔记(4): 使用外部数据
来源于:R学习笔记(4): 使用外部数据 博客:心内求法 鉴于内存的非持久性和容量限制,一个有效的数据处理工具必须能够使用外部数据:能够从外部获取大量的数据,也能够将处理结果保存.R中提供了一系列的函 ...
- SAS之大话PDV
SAS之大话PDV 之所以说是数据源,而非输入缓冲区的原因上一条推送已经说明,这里就不再啰嗦啦. 这里我们且将DATA步流程简单地分为从数据源读入到pdv和从pdv写入数据集. IF语句 & ...
- SAS笔记
SAS基础知识 SAS里面的PROC一览 The ACECLUS Procedure : 聚类的协方差矩阵近似估计(approximate covariance estimation for clus ...
- R语言数据管理(三):数据读入
R的数据读入非常灵活,即可以在R软件中直接输入,也可以读入外部数据. 一.直接输入数据 ①c()函数 ②scan()函数 其功能类似c()函数,scan()实际上是一种键盘输入数据函数.当输入scan ...
- SAS进阶《深入解析SAS》之Base SAS基础、读取外部数据到SAS数据集
SAS进阶<深入解析SAS>之Base SAS基础.读取外部数据到SAS数据集 前言:在学习完<SAS编程与商业案例>后,虽然能够接手公司的基本工作,但是为了更深入的SAS学习 ...
- OpenSceneGraph 笔记--如何导出三角形数据
OpenSceneGraph 笔记--如何导出三角形数据 转载:http://blog.csdn.net/pizi0475/article/details/5384389 在OpenSceneGrap ...
- IOS开发笔记(4)数据离线缓存与读取
IOS开发笔记(4)数据离线缓存与读取 分类: IOS学习2012-12-06 16:30 7082人阅读 评论(0) 收藏 举报 iosiOSIOS 方法一:一般将服务器第一次返回的数据保存在沙盒里 ...
- Python编程从入门到实践笔记——异常和存储数据
Python编程从入门到实践笔记——异常和存储数据 #coding=gbk #Python编程从入门到实践笔记——异常和存储数据 #10.3异常 #Python使用被称为异常的特殊对象来管理程序执行期 ...
随机推荐
- HDU 4055 Number String:前缀和优化dp【增长趋势——处理重复选数】
题目链接:http://acm.hdu.edu.cn/showproblem.php?pid=4055 题意: 给你一个由'I', 'D', '?'组成的字符串,长度为n,代表了一个1~n+1的排列中 ...
- mysql数据库更新
在使用mysql数据库的时候,A方使用一个版本,B方在使用一个版本数据库进行开发使用,B方在开发的时候,有新的需求,需要添加表字段和所需要的表.但是A方已经在使用之前的版本数据库并且数据库里面有真实的 ...
- AngularJS学习笔记(二) 表单验证案例(ng-repeat/filter)
这一节相对来说需要理解的东西不是太多,记住了那些api就行了. 还是一个案例(同样来自miaov),一个表单验证,先上代码,然后再对对应的内容进行解释. <!DOCTYPE html> & ...
- 在开发环境中,自己搭建一个ssl环境(小例子)
做项目的时候自己总结的一些小例子 public class Test { public static void setSSLProperty() { Security.addProvider(new ...
- Smali文件添加try/catch语句,出现“invalid use of move-exception”异常
插入代码如下: 捕获到以下异常: 2019-03-18 21:09:35.431 8272-8272/com.xxxx.xxxx E/AndroidRuntime: FATAL EXCEPTION: ...
- Xposed模块开发学习记录
Xposed模块相关API可以参考在线文档: https://api.xposed.info/reference/packages.html 入门教程可以参考: https://github. ...
- FFmpeg 基本用法
FFmpeg FFmpeg 基本用法 本课要解决的问题 1.FFmpeg的转码流程是什么? 2.常见的视频格式包含哪些内容吗? 3.如何把这些内容从视频文件中抽取出来? 4.如何从一种格式转换为另一种 ...
- 一次spark卡顿分析
在104上面执行,经常会发生卡到了如下一句话: storage.BlockManagerInfo: Added broadcast_8_piece0 当再次卡顿的时候,我直接退出,然后通过yarn看后 ...
- ECMAScript基本函数、概念区分总结
1.使用Number()和parseInt() parseFloat()转换区别. 详见<JavaScript高级程序设计>P30 Number()可以针对任何类型. parseInt() ...
- openstackM版本安装
部署期间常见问题:http://www.cnblogs.com/bfmq/p/6001233.html,问题跟对架构的理解永远比部署重要!你玩技术是绝对是要基于理论的 一.基本情况:物理设备:4台惠普 ...