<?xml version="1.0" encoding="UTF-8"?>
<rss xmlns:content="http://purl.org/rss/1.0/modules/content/" xmlns:dc="http://purl.org/dc/elements/1.1/" xmlns:rdf="http://www.w3.org/1999/02/22-rdf-syntax-ns#" xmlns:taxo="http://purl.org/rss/1.0/modules/taxonomy/" version="2.0">
  <channel>
    <title>topic Re: How to replace missing values with values from another observation by ID. in New SAS User</title>
    <link>https://communities.sas.com/t5/New-SAS-User/How-to-replace-missing-values-with-values-from-another/m-p/950300#M42717</link>
    <description>&lt;P&gt;If the last non-missing value for each ID is acceptable then you can use the UPDATE statement to collapse each variable to last non-missing value.&amp;nbsp; To reload the detailed values of the other variables re-read those observations.&amp;nbsp; You can use a pair of DO loops to do it in one data step.&lt;/P&gt;
&lt;P&gt;&amp;nbsp;&lt;/P&gt;
&lt;P&gt;First let's change the sample data to have a missing value in one of the variables you want excluded from the process, let's pick the second OUTCOME value for ID=2.&lt;/P&gt;
&lt;PRE&gt;&lt;CODE class=" language-sas"&gt;data sample;
  input id sex race eth outcome;
datalines;
1 0 2 1 0
1 . 2 . 1
2 1 . 0 1
2 1 1 0 .
3 . . . 0
3 0 0 1 0
3 0 0 1 1
;&lt;/CODE&gt;&lt;/PRE&gt;
&lt;P&gt;The first loop uses the UPDATE to statement to gather the last non-missing value. Basically it treats a empty version of dataset as the original dataset for which transactions are being applied and the whole dataset as the set of transactions.&amp;nbsp; Then in the second DO loop use the SET statement to re-read the other variables and the OUTPUT statement to generate every observation for this value of ID.&amp;nbsp;&lt;/P&gt;
&lt;P&gt;&amp;nbsp;&lt;/P&gt;
&lt;P&gt;You will need to list either the variables that need updating or those that don't.&amp;nbsp;&lt;/P&gt;
&lt;P&gt;For example you could use a DROP= dataset option to exclude the variables we wanted to "fix" from being reloaded by the SET statement.&lt;/P&gt;
&lt;PRE&gt;&lt;CODE class=" language-sas"&gt;data want;
  do until(last.id);
    update sample(obs=0) sample;
    by id;
  end;
  do until(last.id);
    set sample(drop=sex race eth);
    by id;
    output;
  end;
run;&lt;/CODE&gt;&lt;/PRE&gt;
&lt;P&gt;Results:&lt;/P&gt;
&lt;PRE&gt;&lt;CODE class=" language-sas"&gt;Obs    id    sex    race    eth    outcome

 1      1     0       2      1        0
 2      1     0       2      1        1
 3      2     1       1      0        1
 4      2     1       1      0        .
 5      3     0       0      1        0
 6      3     0       0      1        0
 7      3     0       0      1        1
&lt;/CODE&gt;&lt;/PRE&gt;
&lt;P&gt;If the list of variables to exclude is smaller than the list to include you might change the SET statement to use KEEP= instead.&amp;nbsp; Make sure to keep the ID variable so the BY statement will work.&lt;/P&gt;
&lt;PRE&gt;&lt;CODE class=" language-sas"&gt;    set sample(keep=id outcome);
&lt;/CODE&gt;&lt;/PRE&gt;</description>
    <pubDate>Sat, 09 Nov 2024 17:15:53 GMT</pubDate>
    <dc:creator>Tom</dc:creator>
    <dc:date>2024-11-09T17:15:53Z</dc:date>
    <item>
      <title>How to replace missing values with values from another observation by ID.</title>
      <link>https://communities.sas.com/t5/New-SAS-User/How-to-replace-missing-values-with-values-from-another/m-p/950279#M42713</link>
      <description>&lt;P&gt;I am using SAS 9.4 and have&amp;nbsp; a dataset that has multiple observations for each ID. For whatever reason, some of these individuals have observations which have missing values for variables (i.e., sex, race, ethnicity) that are present in another observation for the same ID.&amp;nbsp;&lt;BR /&gt;&lt;BR /&gt;See below as an example:&amp;nbsp;&lt;/P&gt;
&lt;PRE&gt;&lt;CODE class=" language-sas"&gt;data sample;
input id sex race eth outcome;
datalines;
1 0 2 1 0
1 . 2 . 1
2 1 . 0 1
2 1 1 0 1
3 . . . 0
3 0 0 1 0
3 0 0 1 1
;
RUN;&lt;/CODE&gt;&lt;/PRE&gt;
&lt;P&gt;What I am trying to figure out is how to write code that will replace missing values for specific variables (i.e. sex, race, ethnicity) wherever there is a complete value for another observation for the same ID.&amp;nbsp; Of note, there are some variables that may have differing values by observation (see outcome variable) that I do not want to be changed.&lt;/P&gt;
&lt;P&gt;&amp;nbsp;&lt;/P&gt;
&lt;P&gt;Thank you for your help!&lt;/P&gt;</description>
      <pubDate>Sat, 09 Nov 2024 04:05:25 GMT</pubDate>
      <guid>https://communities.sas.com/t5/New-SAS-User/How-to-replace-missing-values-with-values-from-another/m-p/950279#M42713</guid>
      <dc:creator>sasgorilla</dc:creator>
      <dc:date>2024-11-09T04:05:25Z</dc:date>
    </item>
    <item>
      <title>Re: How to replace missing values with values from another observation by ID.</title>
      <link>https://communities.sas.com/t5/New-SAS-User/How-to-replace-missing-values-with-values-from-another/m-p/950280#M42714</link>
      <description>&lt;P&gt;As I understand it, for each variable (SEX, RACE, ETH) you want to replace instances of missing values with whatever non-missing value is found for that variable and ID.&amp;nbsp; This assumes that no ID has more than one distinct non-missing value for each of those variables.&lt;/P&gt;
&lt;P&gt;&amp;nbsp;&lt;/P&gt;
&lt;P&gt;Pass through each ID twice, first to save non-missing values, and the second to retrieved those saved values:&lt;/P&gt;
&lt;P&gt;&amp;nbsp;&lt;/P&gt;
&lt;PRE&gt;&lt;CODE class=" language-sas"&gt;data sample;
input id sex race eth outcome;
datalines;
1 0 2 1 0
1 . 2 . 1
2 1 . 0 1
2 1 1 0 1
3 . . . 0
3 0 0 1 0
3 0 0 1 1
RUN;

data want (drop=i);
  set sample (in=firstpass)  sample (in=secondpass);
  by id;
  array tmp {3} _temporary_;
  array var {3} sex race eth;
  if first.id then call missing(of tmp{*});
  if firstpass then do i=1 to 3;
    tmp{i}=coalesce(tmp{i},var{i});
  end;
  if secondpass;
  do i=1 to 3;
    var{i}=tmp{i};
  end;
run;&lt;/CODE&gt;&lt;/PRE&gt;
&lt;P&gt;Another, more compact mode, is through use of a MERGE statement, with a merge dataset argument for each variable that needs this type of update.&amp;nbsp; No other code is needed:&lt;/P&gt;
&lt;P&gt;&amp;nbsp;&lt;/P&gt;
&lt;PRE&gt;&lt;CODE class=" language-sas"&gt;data want2;
  merge sample (drop=sex race eth)
        sample (keep=id sex  where=(sex^=.))
        sample (keep=id race where=(race^=.))
        sample (keep=id eth  where=(eth^=.));
  by id;
run;
&lt;/CODE&gt;&lt;/PRE&gt;
&lt;P&gt;&amp;nbsp;&lt;/P&gt;
&lt;P&gt;And if you have, say 20 variables needing this treatment, you can avoid naming the SAMPLE dataset 21 times in the merge statement.&amp;nbsp; You can use the UPDATE statement to prepare one obs per ID, yielding the latest non-missing values for each ID (in dataset NEED).&amp;nbsp; Then merge with the original dataset:&lt;/P&gt;
&lt;PRE&gt;&lt;CODE class=" language-sas"&gt;data need/view=need;
  update sample (keep=id sex race eth  obs=0)
         sample (keep=id sex race eth);
  by id;
run;
data want3;
  merge sample (drop=sex race eth)
        need;
  by id;
run;&lt;/CODE&gt;&lt;/PRE&gt;
&lt;P&gt;Note that NEED is a dataset VIEW, not a dataset FILE.&amp;nbsp; That means it isn't actually executed until NEED is accessed in a later step.&amp;nbsp; As a result, SAMPLE is simultaneously accessed to satisfy the DATA NEED step and the DATA WANT step, minimizing the burden on disk retrieval in the case of large datasets.&amp;nbsp;&amp;nbsp;&lt;/P&gt;
&lt;P&gt;&amp;nbsp;&lt;/P&gt;
&lt;P&gt;&amp;nbsp;&lt;/P&gt;
&lt;P&gt;&amp;nbsp;&lt;/P&gt;
&lt;P&gt;&amp;nbsp;&lt;/P&gt;</description>
      <pubDate>Sat, 09 Nov 2024 05:15:19 GMT</pubDate>
      <guid>https://communities.sas.com/t5/New-SAS-User/How-to-replace-missing-values-with-values-from-another/m-p/950280#M42714</guid>
      <dc:creator>mkeintz</dc:creator>
      <dc:date>2024-11-09T05:15:19Z</dc:date>
    </item>
    <item>
      <title>Re: How to replace missing values with values from another observation by ID.</title>
      <link>https://communities.sas.com/t5/New-SAS-User/How-to-replace-missing-values-with-values-from-another/m-p/950298#M42715</link>
      <description>&lt;P&gt;Use a double DO loop:&lt;/P&gt;
&lt;PRE&gt;&lt;CODE class=" language-sas"&gt;data sample;
input id sex race eth outcome;
datalines;
1 0 2 1 0
1 . 2 . 1
2 1 . 0 1
2 1 1 0 1
3 . . . 0
3 0 0 1 0
3 0 0 1 1
;

data want;
do until (last.id);
  set sample;
  by id;
  _s = coalesce(_s,sex);
  _r = coalesce(_r,race);
  _e = coalesce(_e,eth);
end;
do until (last.id);
  set sample;
  by id;
  sex = _s;
  race = _r;
  eth = _e;
  output;
end;
drop _:;
run;&lt;/CODE&gt;&lt;/PRE&gt;
&lt;P&gt;But since this makes the three variables redundant, you should consider to put them in their own dataset with only one obs per id. Join/merge them in whenever needed.&lt;/P&gt;</description>
      <pubDate>Sat, 09 Nov 2024 14:18:33 GMT</pubDate>
      <guid>https://communities.sas.com/t5/New-SAS-User/How-to-replace-missing-values-with-values-from-another/m-p/950298#M42715</guid>
      <dc:creator>Kurt_Bremser</dc:creator>
      <dc:date>2024-11-09T14:18:33Z</dc:date>
    </item>
    <item>
      <title>Re: How to replace missing values with values from another observation by ID.</title>
      <link>https://communities.sas.com/t5/New-SAS-User/How-to-replace-missing-values-with-values-from-another/m-p/950299#M42716</link>
      <description>&lt;P&gt;Thank you for the multiple options! I started with the middle "compact" code and although I did list out the 10+ variables that worked fine.&amp;nbsp;&lt;/P&gt;
&lt;P&gt;&amp;nbsp;&lt;/P&gt;
&lt;P&gt;Thank you for the quick response.&amp;nbsp;&lt;/P&gt;</description>
      <pubDate>Sat, 09 Nov 2024 14:46:59 GMT</pubDate>
      <guid>https://communities.sas.com/t5/New-SAS-User/How-to-replace-missing-values-with-values-from-another/m-p/950299#M42716</guid>
      <dc:creator>sasgorilla</dc:creator>
      <dc:date>2024-11-09T14:46:59Z</dc:date>
    </item>
    <item>
      <title>Re: How to replace missing values with values from another observation by ID.</title>
      <link>https://communities.sas.com/t5/New-SAS-User/How-to-replace-missing-values-with-values-from-another/m-p/950300#M42717</link>
      <description>&lt;P&gt;If the last non-missing value for each ID is acceptable then you can use the UPDATE statement to collapse each variable to last non-missing value.&amp;nbsp; To reload the detailed values of the other variables re-read those observations.&amp;nbsp; You can use a pair of DO loops to do it in one data step.&lt;/P&gt;
&lt;P&gt;&amp;nbsp;&lt;/P&gt;
&lt;P&gt;First let's change the sample data to have a missing value in one of the variables you want excluded from the process, let's pick the second OUTCOME value for ID=2.&lt;/P&gt;
&lt;PRE&gt;&lt;CODE class=" language-sas"&gt;data sample;
  input id sex race eth outcome;
datalines;
1 0 2 1 0
1 . 2 . 1
2 1 . 0 1
2 1 1 0 .
3 . . . 0
3 0 0 1 0
3 0 0 1 1
;&lt;/CODE&gt;&lt;/PRE&gt;
&lt;P&gt;The first loop uses the UPDATE to statement to gather the last non-missing value. Basically it treats a empty version of dataset as the original dataset for which transactions are being applied and the whole dataset as the set of transactions.&amp;nbsp; Then in the second DO loop use the SET statement to re-read the other variables and the OUTPUT statement to generate every observation for this value of ID.&amp;nbsp;&lt;/P&gt;
&lt;P&gt;&amp;nbsp;&lt;/P&gt;
&lt;P&gt;You will need to list either the variables that need updating or those that don't.&amp;nbsp;&lt;/P&gt;
&lt;P&gt;For example you could use a DROP= dataset option to exclude the variables we wanted to "fix" from being reloaded by the SET statement.&lt;/P&gt;
&lt;PRE&gt;&lt;CODE class=" language-sas"&gt;data want;
  do until(last.id);
    update sample(obs=0) sample;
    by id;
  end;
  do until(last.id);
    set sample(drop=sex race eth);
    by id;
    output;
  end;
run;&lt;/CODE&gt;&lt;/PRE&gt;
&lt;P&gt;Results:&lt;/P&gt;
&lt;PRE&gt;&lt;CODE class=" language-sas"&gt;Obs    id    sex    race    eth    outcome

 1      1     0       2      1        0
 2      1     0       2      1        1
 3      2     1       1      0        1
 4      2     1       1      0        .
 5      3     0       0      1        0
 6      3     0       0      1        0
 7      3     0       0      1        1
&lt;/CODE&gt;&lt;/PRE&gt;
&lt;P&gt;If the list of variables to exclude is smaller than the list to include you might change the SET statement to use KEEP= instead.&amp;nbsp; Make sure to keep the ID variable so the BY statement will work.&lt;/P&gt;
&lt;PRE&gt;&lt;CODE class=" language-sas"&gt;    set sample(keep=id outcome);
&lt;/CODE&gt;&lt;/PRE&gt;</description>
      <pubDate>Sat, 09 Nov 2024 17:15:53 GMT</pubDate>
      <guid>https://communities.sas.com/t5/New-SAS-User/How-to-replace-missing-values-with-values-from-another/m-p/950300#M42717</guid>
      <dc:creator>Tom</dc:creator>
      <dc:date>2024-11-09T17:15:53Z</dc:date>
    </item>
    <item>
      <title>Re: How to replace missing values with values from another observation by ID.</title>
      <link>https://communities.sas.com/t5/New-SAS-User/How-to-replace-missing-values-with-values-from-another/m-p/950309#M42718</link>
      <description>&lt;PRE&gt;&lt;CODE class=" language-sas"&gt;data sample;
input id sex race eth outcome;
datalines;
1 0 2 1 0
1 . 2 . 1
2 1 . 0 1
2 1 1 0 1
3 . . . 0
3 0 0 1 0
3 0 0 1 1
;
proc sql;
create table want as
select id,
coalesce(sex,max(sex)) as sex,
coalesce(race,max(race)) as race,
coalesce(eth,max(eth)) as eth,
outcome
 from sample
  group by id;
quit;&lt;/CODE&gt;&lt;/PRE&gt;</description>
      <pubDate>Sun, 10 Nov 2024 01:48:20 GMT</pubDate>
      <guid>https://communities.sas.com/t5/New-SAS-User/How-to-replace-missing-values-with-values-from-another/m-p/950309#M42718</guid>
      <dc:creator>Ksharp</dc:creator>
      <dc:date>2024-11-10T01:48:20Z</dc:date>
    </item>
  </channel>
</rss>

