2014-09-26 2 views
1

У меня есть набор данных с n уровнями id и (n + 4) переменных. Я хочу выполнить регрессию для каждого из n уровней категориальной переменной, используя значения переменных n-1 в качестве объясняющих переменных. Вот мой набор данных:SAS Выполнение нескольких регрессий и сбор результатов

data have; 
    input s id $ x z y00 y01 y02; 
cards; 
1 00 95 5.00 .02 .43 .33 
2 00 100 5.50 .01 .44 .75 
3 00 110 5.25 .10 .37 .34 
4 00 97 5.00 .02 .43 .33 
5 00 100 5.50 .01 .43 .75 
6 00 120 5.25 .10 .38 .47 
7 00 95 5.00 .02 .43 .35 
8 00 130 5.50 .01 .44 .75 
9 00 110 5.25 .10 .39 .44 
10 00 85 5.00 .02 .43 .33 
11 00 110 5.50 .01 .47 .78 
12 00 110 5.25 .10 .37 .44 
1 01 20 6.00 .22 .01 .66 
2 01 25 5.95 .43 .10 .20 
3 01 70 4.50 .88 .05 .17 
1 02 80 2.50 .65 .33 .03 
2 02 85 3.25 .55 .47 .04 
3 02 90 2.75 .77 .55 .01 
; 
run; 

Так что я хотел бы использовать г, Y01 и Y02 объяснить х для ID 00. Аналогично, г, Y00 и Y02 объясним х для ID 01. Наконец, г, Y00 , и y01 объяснит x для ID 02.

Я могу просто использовать оператор BY, но я не могу придумать, как сказать модели игнорировать переменную с тем же префиксом, что и идентификатор, который я сейчас работать с.

Я мог бы создать отдельные наборы данных, но n> 100 для некоторых из этих анализов.

В идеале, я бы запускал proc mixed и proc reg для каждого ID, как описано выше, и имел набор данных с параметрами для каждого.

Любые идеи?

proc mixed data=have(where=(id='00')) plots(only)=all method=REML nobound ; 
    class s; 
    model x=z y01 y02 
    /solution; 
    random z y01 y02; 
run; 


proc reg data=have(where=(id='00')); 
    model x=z y01 y02; 
run; 

Спасибо.

+0

Вы можете решить эту проблему с макро решение повторно запустить анализ без создания различных наборов данных (на лету, где и модели), но я хотел бы видеть, если кто-то знает лучшее решение; повторное решение макросов будет интенсивным во времени и на диске – Joe

ответ

2

К сожалению, я не знаю, как это сделать без манипуляций с данными, но вот два возможных подхода, которые возникают на ум.

Вариант 1. Скопируйте необходимые независимые переменные в новые переменные.

/* Count the number of y variables */ 
proc sql noprint; 
    select max(input(id, best.)) + 1 
    into :dimY 
    from have; 
quit; 

data alsoHave; 
    set have; 
    /* Create an array for indexing the y variables */ 
    array y[&dimY.] y:; 
    /* Create new variables to contain y values */ 
    array newy[%eval(&dimY.-1)]; 
    _j = 1; 
    do _i = 1 to &dimY.; 
     /* Put each y value in a newy variable where it isn't y_id */ 
     if input(id, best.) + 1 ~= _i then do; 
      newy[_j] = y[_i]; 
      _j + 1; 
     end; 
    end; 
    drop _:; 
run; 

proc reg data = alsoHave; 
    by id; 
    model x = z newy:; 
run; 

Вариант 2. Уменьшить дисперсию нежелательных переменных до 0, чтобы они не повлияли на регрессию.

data alsoHave; 
    set have; 
    /* Create an array for indexing the y variables */ 
    array y[*] y:; 
    _i = input(id, best.) + 1; 
    backUp = y[_i]; 
    /* Overwrite the unwanted variables with 0 */ 
    y[_i] = 0; 
    drop _:; 
run; 

proc reg data = alsoHave; 
    by id; 
    model x = z y:; 
run; 

Я предпочитаю простоту варианта 2, но программирование массивов - это весело, поэтому я включил вариант 1 в любом случае.

Редактировать: Ниже приведена версия агностической версии Варианта 2, не требующая последовательных целых чисел. Интересными функциями являются dim(), который возвращает число переменных в массиве и vname(), который возвращает имя переменной из массива и индекса. Наконец compress() используется с опциями k (сохранить) и d (цифры). Подобные изменения могут быть внесены Вариант 1.

data alsoHave; 
    set have; 
    /* Create an array for indexing the y variables */ 
    array y[*] y:; 
    /* Loop through the y variables */ 
    do _i = 1 to dim(y); 
     /* Replace with 0 when the variable name matches the id */ 
     if input(compress(vname(y[_i]), , "dk"), best.) = input(id, best.) then y[_i] = 0; 
    end; 
    drop _:; 
run; 
+0

Ошибка с моей стороны не упоминать, что идентификаторы не всегда будут последовательными. Возможно, идентификаторы для одной регрессии - это 01, 25, 145 и т. Д. Любые идеи, как изменить свое решение, чтобы справиться с этим, не создавая dummyname для id? В противном случае, отличные решения. – pyll

+1

Я добавил третий пример, который должен соответствовать вашим потребностям. Если вы планируете делать много программных массивов SAS, это очень полезный инструмент и стоит [исследовать] (http://support.sas.com/resources/papers/97529_Using_Arrays_in_SAS_Programming.pdf). – SRSwift

+0

Это очень полезно. Спасибо. Мне определенно нужно работать над программированием массива. Варианты 2 и 3 очень умны, хотя я думаю, что предпочитаю вариант 1. Я использовал ваши предложения в варианте 3, чтобы изменить вариант 1, но все еще есть проблема: я теряю суффикс, соответствующий каждой переменной. Таким образом, код создает newy1 и newy2, которые отлично подходят для id = 00. Однако, когда id = 01, переменная y00 называется newy1.Поэтому я теряю интерпретацию в результате, так как newy не всегда соответствует поясняющей переменной, которую я хочу. Думаю, вариант 3 работает лучше всего здесь. Спасибо за помощь. – pyll