как разделить большой набор данных как можно быстрее - PullRequest
1 голос
/ 02 апреля 2019

У меня очень большой набор данных размером 1T, мне нужно быстро разбить его на несколько наборов данных.

Ниже приводится традиционный способ разделения набора данных:

Data d1 d2...dn;
Set raw_dataset;
if condition1 then output d1;
else if condition2 then output d2;
...
else if conditionN then output dn;
run;

но это все еще слишком медленно для меня !!
Есть ли способ ускорить процесс?

Ответы [ 2 ]

0 голосов
/ 02 апреля 2019

Если вы не хотите использовать условия, я могу поделиться с вами этим макросом, который я использую с 3 лет:

%macro partitionner(Library=, Table=, nb_part=, nblig=, tabIntr=);
data 
    %do i=1 %to &nb_part; 
        &Library..&tabIntr.&i. 
     %end;
; 
      set &Library..&Table.; 

      %do i=1 %to %eval(&nb_part-1); 
         if _n_ >= %eval(1+(&i.-1)*&nblig.) and _n_ <= %eval(&i.*&nblig.) 
         then output &Library..&tabIntr.&i.; 
      %end; 
      if _n_>=%eval((&i.-1)*&nblig+1) then output &lib..&tabIntr.&nb_part.; 
   run;
%mend partitionner;

где:

  • Библиотека: имя библиотеки, в которой находится таблица для разделения, и результаты.
  • Таблица: имя таблицы для разделения.
  • nb_part: количество таблиц, которые должны быть разбиты.являются результатами от разделения.
  • nblig: количество строк в каждой выходной таблице.
  • tabIntr: имя выходных таблиц (префикс).

пример:

bigTable имеет 100 строк и находится в библиотеке LIBRA.Хотите разделить его на 4 таблицы, каждая из которых имеет 33 строки.

%partitionner(Library=LIBRA, Table=bigTable, nb_part=4, nblig=33, tabIntr=smalTable);

Результат:

  • smallTable1 имеет 33 наблюдения.
  • smallTable2 имеет 33наблюдения.
  • smallTable3 имеет 33 наблюдения.
  • smallTable4 имеет 1 наблюдения.
0 голосов
/ 02 апреля 2019

Вы можете использовать следующий макрос, просто введите два параметра 1. входной набор данных, который вы хотите разделить 2. введите максимальное количество наблюдений, которое вам нужно в каждом наборе данных

options merror mprint symbolgen mlogic;

/****CHANGE PATH for input DS location****/
libname inp "Y:\InputDS";
libname outp "Y:\OutputDS";

data inp_ds;
 set inp.input_sample; /****CHANGE Input DS****/
run;

proc sql noprint;
select count(*) into: total_obs from inp_ds;
quit;

%let max_obs=20000; /****CHANGE max number of OBS in a split DS****/
%let split_ds_num_temp=%sysfunc(int(&total_obs/&max_obs));
%let remainder= %sysfunc(mod(&total_obs,&max_obs));

data find_num;
 if &remainder>0 then split_ds_num=&split_ds_num_temp+1;
 else split_ds_num=&split_ds_num_temp;
 call symput('no_of_splits',split_ds_num);
run;

%macro split(i,inds);
data outp.out&i;
 set &inds;
 %if &i=1 %then 
 %do;
    If _N_>=1 and _N_<=&max_obs Then Output;
 %end;
 %else %if &i>1 %then
 %do;
    If _N_ >=(&max_obs*(&i-1))+1 and _N_<=&max_obs*&i Then Output;
 %end;
run;
%mend split;

data initiate_macro;
do i = 1 to &no_of_splits;
    call execute('%split('||i||', inp_ds)');
end;
run;

Это создаст несколько выходных наборов данных в виде: out1 out2 ... outn .. в зависимости от количества наблюдений в пути к выходному каталогу, указанному в вашей программе

...