SAS編程:通過(guò)Picture語(yǔ)句設(shè)置變量Format

輸出一張頻數(shù)匯總表,遇到一個(gè)問(wèn)題。TFLShell中兆衅,頻數(shù)百分比保留一位小數(shù),我直接用5.1的格式將百分比put出來(lái) (put(percent, 5.1))嗜浮。這樣做羡亩,本來(lái)沒(méi)什么問(wèn)題。但這張表的BigN大于1000危融,分類中有頻數(shù)為0和1的情況畏铆,這樣對(duì)于頻數(shù)為0和1的類別,百分比輸出都為“(0.0)”吉殃,直觀上看這兩個(gè)百分比相同辞居。

跟統(tǒng)計(jì)師進(jìn)行確認(rèn)楷怒,對(duì)于頻數(shù)不為0的記錄,如果頻率小于0.1瓦灶,顯示為“(<0.1)”鸠删。這樣,頻率百分比顯示要求具體如下:

  1. 對(duì)于>0以及<0.1的值贼陶,顯示“<0.1”;
  2. 對(duì)于0或≥0.1的值刃泡,顯示5.1的格式。

對(duì)于每一個(gè)試驗(yàn)分組碉怔,我目前的代碼如下:

c1 = strip(put(_0, 5)) || " (" || strip(put(_0/&n_0.*100, 5.1)) ||")";

基于新的邏輯捅僵,我需要判斷頻數(shù)是否為0,以及頻率是否小于0.1之后眨层,再進(jìn)行賦值庙楚。同時(shí),5個(gè)不同的試驗(yàn)分組需要單獨(dú)處理趴樱。

直接進(jìn)行條件判斷馒闷,程序更新比較繁瑣,所以我考慮通過(guò)設(shè)置百分比的Format來(lái)實(shí)現(xiàn)統(tǒng)計(jì)師的要求叁征。設(shè)置好符合條件的Format之后纳账,直接替換格式5.1,就可以完成程序的更新捺疼。

而這個(gè)格式的設(shè)置疏虫,就是通過(guò)Format過(guò)程步中的pircture語(yǔ)句來(lái)實(shí)現(xiàn)。

這里為什么不能使用value語(yǔ)句來(lái)設(shè)置Format呢啤呼?value語(yǔ)句設(shè)置的Format卧秘,是固定的值或范圍對(duì)應(yīng)具體的字符串,而條件2顯示具體的格式官扣,是無(wú)法用value語(yǔ)句實(shí)現(xiàn)的翅敌。

下面開(kāi)始介紹Format過(guò)程步中的Picture語(yǔ)句,讀者也可以直接跳到第4部分惕蹄,先看一下Picture語(yǔ)句的具體應(yīng)用蚯涮。

0. Picture語(yǔ)句語(yǔ)法

Picture語(yǔ)句是用于創(chuàng)建輸出數(shù)值的模板 (Creates a template for printing numbers.),其主要語(yǔ)法為:

proc format;
  picture fmtname
  value-or-range-1 = 'picture-1'
  value-or-range-2 = 'picture-2'
    ... ...
  ;
run;

1. value-or-range

等號(hào)左側(cè)的value-or-range, 有兩類形式卖陵,一是具體的值遭顶,二是具體的范圍。具體的離散值不做詳細(xì)的介紹泪蔫,具體的范圍主要有三種形式:

  1. 范圍端點(diǎn)包含無(wú)限值(正無(wú)窮或負(fù)無(wú)窮)棒旗,舉例:0-high, low-0, low-high;
  2. 范圍端點(diǎn)為有限值鸥滨,且包含有限值嗦哆,舉例:0-1,1-100婿滓,-1-6
  3. 范圍端點(diǎn)為有限值老速,但不包含有限值,舉例:0<-1, 1-<100, -1<-<6凸主。

同時(shí)橘券,value-or-range的兩類形式可以互相并列,中間用,間隔:

proc format;
  picture fmtname
  1,3, 4-10 = 'picture1'
  11-20, 21 = 'picture2'
  ;
run;

2. 'Picture'

等號(hào)右側(cè)的'Picture'可以理解成一種具體的數(shù)值模板卿吐,主要有3類:

  1. 數(shù)值選擇符 (digit selectors)旁舰;
  2. 信息字符 (message characters)
  3. 指令 (directives)
2.1 數(shù)值選擇符 (digit selectors);

數(shù)值選擇符嗡官,用于定義數(shù)值位置的0-9的字符箭窜,1個(gè)選擇符代表1位數(shù)字。如果是非0選擇符在最左側(cè)衍腥,不足位的數(shù)值將會(huì)用0補(bǔ)位磺樱;如果是0選擇符在最左側(cè),不足位的數(shù)值將不會(huì)用0補(bǔ)位婆咸;通常用數(shù)字9來(lái)表示非0字符竹捉。代碼示例如下:

proc format;
  picture fmt
    1-5 = '009.9'
    5<-10 = '999.9'
  ;
run;

data tmp;
    a = 1; b = put(a, fmt.); output; 
    a = 10; b = put(a, fmt.); output;
run;
tmp

格式fmt的含義為,對(duì)于1到5之間的數(shù)值尚骄,保留1位小數(shù)块差;對(duì)于5到10之間的數(shù)據(jù)值,保留1位小數(shù)倔丈,如果小數(shù)點(diǎn)左側(cè)位數(shù)小于3位憨闰,則用0補(bǔ)位。

數(shù)值1的格式為0選擇符在最左側(cè)需五,整數(shù)位不足3位時(shí)起趾,不需要用0補(bǔ)足位數(shù);數(shù)值10的格式為非0選擇符在最左側(cè)警儒,整數(shù)位不足3位時(shí)训裆,需要用0補(bǔ)足位數(shù)。

2.2 信息字符 (message characters)蜀铲;

信息字符边琉,是指非數(shù)字字符,直接輸出字符串的內(nèi)容记劝,這類似于Value語(yǔ)句生成的格式变姨。

proc format;
  picture fmt
    1-5 = 'ha'
    5<-10 = 'hei'
  ;
run;

data tmp;
    a = 1; b = put(a, fmt.); output; 
    a = 10; b = put(a, fmt.); output;
run;
tmp

Picture模板中,也可以同時(shí)包括數(shù)值選擇符和信息字符厌丑,不過(guò)數(shù)值字符必須在模板的開(kāi)頭定欧,這樣數(shù)值選擇符的格式才能正常顯示渔呵。

proc format;
  picture fmt
    1-5 = '000.00 ha'
    5<-10 = '999.9 hei'
  ;
run;

data tmp;
    a = 1; b = put(a, fmt.); output; 
    a = 10; b = put(a, fmt.); output;
run;
tmp
2.3 指令 (directives);

指令砍鸠,是一些特殊字符扩氢,可以用來(lái)格式化日期、時(shí)間或日期時(shí)間值爷辱。這一內(nèi)容在日常工作中录豺,比較少用到,這里不做過(guò)多介紹饭弓,感興趣的讀者可以自行查看SAS官方文檔(SAS Help Center: Syntax: PROC FORMAT PICTURE Statement)双饥。

3. 常用選項(xiàng)

Picture語(yǔ)句中的選項(xiàng),分為Format選項(xiàng)和Picture選項(xiàng)弟断。在Format過(guò)程步使用選項(xiàng)時(shí)咏花,要將選項(xiàng)放置到括號(hào)()中。Format選項(xiàng)放在格式名稱之后阀趴,Picture選項(xiàng)放在模板'Picture'之后迟螺。介紹3個(gè)常用選項(xiàng),Round舍咖,Noedit以及Prefix=""矩父。

3.1 Format選項(xiàng)——Round

Round選項(xiàng)的作用是,對(duì)數(shù)值進(jìn)行格式化時(shí)排霉,會(huì)將數(shù)值四舍五入到最近的整數(shù)窍株。直接看定義不方便理解,直接看代碼演示:

**Without Round option;
proc format;
  picture fmt
    1-5 = '000.00'
    5<-10 = '999.99 '
  ;
run;

data tmp1;
  a = 1.444; b = put(a, fmt.); output; 
  a = 1.445; b = put(a, fmt.); output;

  a = 9.444; b = put(a, fmt.); output; 
  a = 9.445; b = put(a, fmt.); output;
run;
tmp1

未使用Round選項(xiàng)時(shí)攻柠,對(duì)數(shù)值進(jìn)行保留兩位小數(shù)的操作球订,會(huì)直接取小數(shù)位的后兩位,不管小數(shù)點(diǎn)后第3位數(shù)值的大小瑰钮。

**With Round option;
proc format;
  picture fmt (round)
    1-5 = '000.00'
    5<-10 = '999.99 '
  ;
run;

data tmp2;
  a = 1.444; b = put(a, fmt.); output; 
  a = 1.445; b = put(a, fmt.); output;

  a = 9.444; b = put(a, fmt.); output; 
  a = 9.445; b = put(a, fmt.); output;
run;
tmp2

使用Round選項(xiàng)后冒滩,對(duì)數(shù)值進(jìn)行保留兩位小數(shù)的操作,會(huì)根據(jù)小數(shù)點(diǎn)后第3位數(shù)值的大小進(jìn)行四舍五入浪谴。代碼示例中开睡,第3位為5時(shí),會(huì)向前進(jìn)一位苟耻。

3.2 Picture選項(xiàng)——Noedit

Noedit選項(xiàng)作用是篇恒,將Picture模板中的數(shù)值當(dāng)做信息字符 (message characters),而不是數(shù)值選擇符 (digit selectors)凶杖。前面介紹到胁艰,模板中的數(shù)字都有對(duì)應(yīng)的含義,Noedit選項(xiàng)會(huì)抹去模板中數(shù)字的含義,直接將數(shù)字當(dāng)作純粹的字符腾么,與Value語(yǔ)句生成Format的作用完全相同奈梳。

代碼舉例如下:

**Noedit option;
proc format;
  picture fmt
    1-5 = '000.00 ha' (noedit)
    5<-10 = '999.9 hei'
  ;
run;

data tmp;
    a = 1; b = put(a, fmt.); output; 
    a = 10; b = put(a, fmt.); output;
run;
tmp

數(shù)字1的Format,對(duì)應(yīng)字符000.00 ha解虱;數(shù)字10的Format攘须,對(duì)應(yīng)保留1位小數(shù),并在數(shù)值后面添加字符"hei"饭寺。

3.3 Picture選項(xiàng)——Prefix=

Prefix=選項(xiàng)的作用是阻课,指定一個(gè)字符作為格式化值的前綴叫挟。這個(gè)比較容易理解艰匙,直接看代碼實(shí)例,輸出結(jié)果中直接添加前綴中的內(nèi)容抹恳。關(guān)于Prefix=選項(xiàng)的具體應(yīng)用员凝,我們?cè)谙乱徊糠纸榻B。

**Prefix= option;
proc format;
  picture fmt
    1-5 = '000.00' (prefix = "Haha - ")
    5<-10 = '999.99' (prefix = "Heihei - ")
  ;
run;

data tmp;
    a = 1; b = put(a, fmt.); output; 
    a = 10; b = put(a, fmt.); output;
run;
tmp

4. Picture語(yǔ)句應(yīng)用舉例

4.1 頻率格式自帶括號(hào)——Prefix=

通常我們?cè)谳敵鲱l數(shù)匯總時(shí)奋献,頻數(shù)和頻率的輸出都是以n (xx.x)的形式輸出健霹。常規(guī)的做法是將數(shù)值Put出來(lái)后,與左右括號(hào)進(jìn)行拼接瓶蚂。

c1 = strip(put(_0, 5)) || " (" || strip(put(_0/&n_0.*100, 5.1)) ||")";

通過(guò)Picture語(yǔ)句生成的頻率格式也可以自帶括號(hào)糖埋,這需要Prefix選項(xiàng)來(lái)實(shí)現(xiàn)

前面談到窃这,'Picture'模板瞳别,可以同時(shí)使用數(shù)值選擇符和信息字符,但是數(shù)值選擇符必須位于模板的開(kāi)頭杭攻。

特定范圍的數(shù)值可以使用數(shù)值選擇符設(shè)置特定的格式祟敛,后面添加信息字符右括號(hào)),而開(kāi)頭的左括號(hào)可以通過(guò)prefix="( "選項(xiàng)來(lái)實(shí)現(xiàn)兆解。

具體演示代碼如下馆铁,F(xiàn)ormat選項(xiàng)中min =選項(xiàng)指定格式的最小長(zhǎng)度。如果不指定長(zhǎng)度的話锅睛,默認(rèn)長(zhǎng)度是第一條記錄Format值的長(zhǎng)度埠巨,這可能造成后續(xù)值的截?cái)唷?/p>

代碼中也展示了手動(dòng)輸出括號(hào)的結(jié)果,兩者的顯示略有區(qū)別现拒。使用Picture格式的輸出乖订,左括號(hào)始終距離數(shù)字1個(gè)空格;而手動(dòng)輸出括號(hào)的方法具练,左括號(hào)的位置始終固定乍构。

具體如何展示,需要看各個(gè)公司、項(xiàng)目哥遮、統(tǒng)計(jì)師的要求岂丘,不能一概而論。

proc format;
  picture fmt (round min = 10)
    0-<99.95 = '009.9 )'  (prefix = "( ")
    99.95-100 = '999.9 )'  (prefix = "( ")
  ;
run;

data tmp1;
    a = 0.15; b = put(a, fmt.); output; 
    a = 10.15; b = put(a, fmt.); output; 
    a = 99.92; b = put(a, fmt.); output;
    a = 99.96; b = put(a, fmt.); output;
run;

data tmp2;
    a = 0.15; b = "( " || put(a, 5.1) || " ) "; output; 
    a = 10.15; b = "( " || put(a, 5.1) || " ) "; output; 
    a = 99.92; b = "( " || put(a, 5.1) || " ) "; output;
    a = 99.96; b = "( " || put(a, 5.1) || " ) "; output;
run;
tmp1
tmp2
4.2 頻率輸出演示

最近手頭項(xiàng)目的要求眠饮,頻率百分比大于0且小于0.1奥帘,輸出為<0.1;其他則輸出保留1位小數(shù)仪召。

具體實(shí)現(xiàn)的代碼如下:

proc format;
  picture fmt (round min = 10)
    0<-<0.1 = '( <0.1 )'  (noedit)
    0, 0.1-high = '009.9 )'  (prefix = "( ")
  ;
run;

data tmp;
    a = 0.05; b = put(a, fmt.); output; 
    a = 0; b = put(a, fmt.); output; 
    a = 90.15; b = put(a, fmt.); output;
    a = 99.96; b = put(a, fmt.); output;
run;
tmp

取值為0與≥0.1的Format值相同寨蹋,設(shè)置格式時(shí)可以使用,進(jìn)行并列。Format選項(xiàng)round使保留小數(shù)位時(shí)扔茅,進(jìn)行四舍五入已旧。

4.3 p值輸出演示

醫(yī)學(xué)期刊一般對(duì)p值的輸出有要求,例如:

  1. p > 0.1, p值保留2位小數(shù)召娜;
  2. 0.1 > p ≥ 0.001运褪,p值保留3位小數(shù);
  3. p < 0.001玖瘸,p值顯示為"p < 0.001"秸讹。

實(shí)現(xiàn)代碼如下:

proc format;
  picture fmt (round min = 10)
    0-<0.001 = 'p < 0.001'  (noedit)
    0.001-<0.01 = '9.999'  
    0.01-1 = '9.99'
  ;
run;

data tmp;
    a = 0.0005; b = put(a, fmt.); output; 
    a = 0.0015; b = put(a, fmt.); output; 
    a = 0.624; b = put(a, fmt.); output;
    a = 0.625; b = put(a, fmt.); output;
run;
tmp

總結(jié)

這篇文章介紹了Format過(guò)程步中Picture語(yǔ)句基本語(yǔ)法,Pircture語(yǔ)句生成的Format與Value語(yǔ)句生成的不同雅倒,模板設(shè)置的多樣性可以應(yīng)對(duì)更加復(fù)雜的格式要求璃诀。文章還介紹了3個(gè)常用的選項(xiàng),以及3個(gè)Picture語(yǔ)句的應(yīng)用舉例蔑匣。

希望給讀者在日常工作中一些思路啟發(fā)劣欢,提供不一樣的解決格式問(wèn)題的視角。

感謝閱讀殖演!若有疑問(wèn)氧秘,歡迎評(píng)論區(qū)交流!

最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請(qǐng)聯(lián)系作者
  • 序言:七十年代末趴久,一起剝皮案震驚了整個(gè)濱河市丸相,隨后出現(xiàn)的幾起案子,更是在濱河造成了極大的恐慌彼棍,老刑警劉巖灭忠,帶你破解...
    沈念sama閱讀 206,126評(píng)論 6 481
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件,死亡現(xiàn)場(chǎng)離奇詭異座硕,居然都是意外死亡弛作,警方通過(guò)查閱死者的電腦和手機(jī),發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 88,254評(píng)論 2 382
  • 文/潘曉璐 我一進(jìn)店門华匾,熙熙樓的掌柜王于貴愁眉苦臉地迎上來(lái)映琳,“玉大人,你說(shuō)我怎么就攤上這事∪鳎” “怎么了有鹿?”我有些...
    開(kāi)封第一講書(shū)人閱讀 152,445評(píng)論 0 341
  • 文/不壞的土叔 我叫張陵,是天一觀的道長(zhǎng)谎脯。 經(jīng)常有香客問(wèn)我葱跋,道長(zhǎng),這世上最難降的妖魔是什么源梭? 我笑而不...
    開(kāi)封第一講書(shū)人閱讀 55,185評(píng)論 1 278
  • 正文 為了忘掉前任娱俺,我火速辦了婚禮,結(jié)果婚禮上废麻,老公的妹妹穿的比我還像新娘荠卷。我一直安慰自己,他們只是感情好脑溢,可當(dāng)我...
    茶點(diǎn)故事閱讀 64,178評(píng)論 5 371
  • 文/花漫 我一把揭開(kāi)白布僵朗。 她就那樣靜靜地躺著赖欣,像睡著了一般屑彻。 火紅的嫁衣襯著肌膚如雪。 梳的紋絲不亂的頭發(fā)上顶吮,一...
    開(kāi)封第一講書(shū)人閱讀 48,970評(píng)論 1 284
  • 那天社牲,我揣著相機(jī)與錄音,去河邊找鬼悴了。 笑死搏恤,一個(gè)胖子當(dāng)著我的面吹牛,可吹牛的內(nèi)容都是我干的湃交。 我是一名探鬼主播熟空,決...
    沈念sama閱讀 38,276評(píng)論 3 399
  • 文/蒼蘭香墨 我猛地睜開(kāi)眼,長(zhǎng)吁一口氣:“原來(lái)是場(chǎng)噩夢(mèng)啊……” “哼搞莺!你這毒婦竟也來(lái)了息罗?” 一聲冷哼從身側(cè)響起,我...
    開(kāi)封第一講書(shū)人閱讀 36,927評(píng)論 0 259
  • 序言:老撾萬(wàn)榮一對(duì)情侶失蹤才沧,失蹤者是張志新(化名)和其女友劉穎迈喉,沒(méi)想到半個(gè)月后,有當(dāng)?shù)厝嗽跇?shù)林里發(fā)現(xiàn)了一具尸體温圆,經(jīng)...
    沈念sama閱讀 43,400評(píng)論 1 300
  • 正文 獨(dú)居荒郊野嶺守林人離奇死亡挨摸,尸身上長(zhǎng)有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點(diǎn)故事閱讀 35,883評(píng)論 2 323
  • 正文 我和宋清朗相戀三年,在試婚紗的時(shí)候發(fā)現(xiàn)自己被綠了岁歉。 大學(xué)時(shí)的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片得运。...
    茶點(diǎn)故事閱讀 37,997評(píng)論 1 333
  • 序言:一個(gè)原本活蹦亂跳的男人離奇死亡,死狀恐怖,靈堂內(nèi)的尸體忽然破棺而出熔掺,到底是詐尸還是另有隱情彬檀,我是刑警寧澤,帶...
    沈念sama閱讀 33,646評(píng)論 4 322
  • 正文 年R本政府宣布瞬女,位于F島的核電站窍帝,受9級(jí)特大地震影響,放射性物質(zhì)發(fā)生泄漏诽偷。R本人自食惡果不足惜坤学,卻給世界環(huán)境...
    茶點(diǎn)故事閱讀 39,213評(píng)論 3 307
  • 文/蒙蒙 一、第九天 我趴在偏房一處隱蔽的房頂上張望报慕。 院中可真熱鬧深浮,春花似錦、人聲如沸眠冈。這莊子的主人今日做“春日...
    開(kāi)封第一講書(shū)人閱讀 30,204評(píng)論 0 19
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽(yáng)蜗顽。三九已至布卡,卻和暖如春,著一層夾襖步出監(jiān)牢的瞬間雇盖,已是汗流浹背忿等。 一陣腳步聲響...
    開(kāi)封第一講書(shū)人閱讀 31,423評(píng)論 1 260
  • 我被黑心中介騙來(lái)泰國(guó)打工, 沒(méi)想到剛下飛機(jī)就差點(diǎn)兒被人妖公主榨干…… 1. 我叫王不留崔挖,地道東北人贸街。 一個(gè)月前我還...
    沈念sama閱讀 45,423評(píng)論 2 352
  • 正文 我出身青樓,卻偏偏與公主長(zhǎng)得像狸相,于是被迫代替她去往敵國(guó)和親薛匪。 傳聞我的和親對(duì)象是個(gè)殘疾皇子,可洞房花燭夜當(dāng)晚...
    茶點(diǎn)故事閱讀 42,722評(píng)論 2 345

推薦閱讀更多精彩內(nèi)容