SAS date imported wrong

假装没事ソ 提交于 2021-01-28 10:51:03

问题


When I imported my excel sheet some dates imported differently than others. I tried to fix this with the code below to format the date.

DATA volume;
SET mice.volume;
format Date MMDDYY10.;
run;

However, I received the following error.

ERROR 48-59: The format $MMDDYY was not found or could not be loaded.

I had also tried with the following code

DATA volume;
SET mice.volume;
If date= 44138 then date= '11/3';
If date= 44141 then date= '11/6';
run;

NOTE: Character values have been converted to numeric values at the places given by: (Line):(Column).

A Proc Contents shows the variable= Date type= Char Len=7 format=$7 Informat=$7 Label= Date

How do I fix this?


回答1:


The date column being character having a mix of 'date looking' strings, and Excel date value numbers tells me some of the date values in your Excel are actually strings, such as '11/10 or ='11/10'.

The raw number 44138 is:

  • a SAS date value is 04-NOV-2080 (obviously not what is wanted)
  • an Excel date value 03-NOV-2020 (aha!)
  • 03-NOV-2020 as SAS date value is 22222
    • an offset of -21916 from Excel
  • -21916 is the SAS date 30-DEC-1899

Date Epochs

An epoch is the date corresponding to a base number 0 in a systems calendar.
SAS Base year is 1960 and Excel Base year is 1900.

                     Formatted 
Number  Actual Date  Date Shown   System/Format
------  -----------  -----------  ----------
     0  31-DEC-1899  1/0/1900     Excel / Short Date (Formatter is weird at Epoch)
     0  01-JAN-1960  01-JAN-1960  SAS / DATE11.
 21916  01-JAN-1960  1/1/1960     Excel / Short Date
-21916  30-DEC-1899  31-DEC-1899  SAS / DATE11.

Notice the round trip is from 31-dec-1899 to 30-dec-1899. This due to an Excel 97 bug that has been carried forth for legacy reasons. See Microsoft's explanation in "Excel incorrectly assumes that the year 1900 is a leap year" which pushes the blame back even further to Lotus 1-2-3

The formula to convert between systems S1 and S2 date numbers is to add the # for the other systems epoch date (@ # 0)

SAS#(date) = Excel#(date) + SAS#(Excel Epoch Date) - 1 (Excel leap year bug), or
sas_dt = excel_dt + '31-DEC-1899'd - 1; *or;
sas_dt = excel_dt + '30-DEC-1899'd;

What happened

Mixed value types in the Excel date column forced IMPORT to perceive the date variable as character.

  • The Excel cells with a date looking m/d string were brought in as the string
  • The Excel cells with a date, likely custom formatted as m/d, were brought in as the underlying Excel date number.

The ERROR

You tried to apply the date format MMDDYY. to the character variable Date. A character column can not be assigned a numeric or date format, thus you get the

ERROR 48-59: The format $MMDDYY was not found or could not be loaded.

SAS automatically presumed MMDDYY. meant a character format $MMDDYY. because the variable type was character.

The Fix

You can convert the values in the character date column with code such as the following (untested):

  if index(date,'/') then 
    date_fixed = input (trim(date)||'/2020', mmddyy10.);
  else 
    date_fixed = input(date,best12.) + '30-DEC-1899'D;

  format date_fixed yymmdd10.;

If you want to continue showing only mm/dd in SAS, use the format NLDATEM5.

  format date_fixed NLDATEM5.;


来源:https://stackoverflow.com/questions/64979048/sas-date-imported-wrong

标签
易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!