データセットの一部は次のとおりです。
Obs Buffer
...
75 14
76 13
77 64
78 38.1%
79 29.2%
80 69.2%
81 33
82 5-12
...
「%」を含むデータと、その前の 2 行だけが必要です。例えばこの場合「13」「64」「38.1%」「29.2%」「69.2%」を抜き出したい。
これを達成する方法はありますか?
こういう使い方point
が好きです。 _N_
データステップループで何かおかしいことをしていない限り、行カウンターとして信頼できます。
data have;
length buffer $50;
input obs buffer $;
datalines;
75 14
76 13
77 64
78 38.1%
79 29.2%
80 69.2%
81 33
82 5-12
;;;;
run;
data want;
set have;
pointer=_N_;
if find(buffer,'%') then do;
output;
pointer=_N_-1;
set have point=pointer;
if not (find(buffer,'%')) then do;
output;
pointer=_N_-2;
set have point=pointer;
if not (find(buffer,'%')) then output;
end;
end;
run;
順序を復元する必要がある場合は、pointer
後で並べ替えることができます(またはobs
、それが実際の変数の場合-そうではないと思います)。obs
が実際の変数である場合 (またはビューで実際の変数にする場合)、これを行う SQL の興味深い方法があります。
proc sql;
create table want as
select H.* from have H
left join have V on H.obs=V.obs-1
left join have A on H.obs=A.obs-2
where
(find(H.buffer,'%'))
or
(find(V.buffer,'%'))
or
(find(A.buffer,'%'))
order by H.obs
;
quit;
データパスなしで obs をリアルにする方法:
data have_vw/view=have_vw;
set have;
obs=_n_;
run;
そして、have_vw
代わりにhave
SQL クエリで使用します (3 つの場所すべてで)。
kungfujam の考えに従って、以下のコードを取得し、動作します。
data adjust;
set source;
oneBefore = lag1(Buffer);
twoBefore = lag2(Buffer);
threeBefore = lag3(Buffer);
fourBefore = lag4(Buffer);
if index(buffer,'%')^=0 and index(onebefore,'%')^=0 and index(twobefore,'%')^=0then do;
x = fourBefore;
output;
x = threeBefore;
output;
x = twoBefore;
output;
x = oneBefore;
output;
x=buffer;
output;
end;
keep x;
run;
あなたの質問に答えるには:_N_
変数は、データ ステップがデータ ステートメントを超えてループした回数を返します。( http://support.sas.com/documentation/cdl/en/lrcon/62955/HTML/default/viewer.htm#a000695104.htm )
ただし、問題を解決するにはlag()
( http://support.sas.com/documentation/cdl/en/lrdict/64316/HTML/default/viewer.htm#a000212547.htm ) を使用し、contains ステートメントなどを使用します。
data justBuffers;
set yourDS;
twoBefore = lag2(Buffer);
oneBefore = lag1(Buffer);
if Buffer ? '%' then do;
if not missing(twoBefore) then do;
x = twoBefore;
output;
end;
if not missing(oneBefore) then do;
x = oneBefore;
output;
end;
x = Buffer;
output;
call missing(oneBefore, twoBefore);
end;
keep x;
run;
私はコードをテストしていないので気をつけてください! きっとスムーズにできます。