SAS PROC 导入多个 SAV 文件 - 强制 SPSS 值标签创建唯一的 SAS 格式名称

SAS PROC IMPORT Multiple SAV Files- Force SPSS Value Labels to Create UNIQUE SAS Format Names

有时,如果我将多个 SAV 文件导入 SAS 工作库,稍后导入的一个变量会覆盖较早导入的具有相似名称的变量的显示文本(即格式)。

我确定这是因为后来数据集的变量为自定义格式(来自 SPSS Values Labels)生成了一个 格式名称,与 相同来自早期变量的格式名称,即使这些变量在 SAV 文件的值标签属性中具有不同的定义。

有没有办法通过在自动命名新的自定义格式之前在 PROC IMPORT 自动检查格式名称是否已经存在于工作库格式库中来强制 SAS 不重复使用相同的格式名称?或者还有其他方法可以防止这种情况发生吗?

这是我的代码以及变量名、格式名等的示例

proc import out=Dataset1 datafile="S:\folder\Dataset1.SAV"
dbms=SAV replace; 
run;
proc import out=DatasetA datafile="S:\folder\DatasetA.SAV"
dbms=SAV replace; 
run;

数据集 1 包含变量 Question_1。原始 SPSS 值标签为 1=Yes 2=No。导入此数据集时,SAS 会自动生成格式名称 QUESTION., for Question_1。只导入Dataset1时,格式QUESTION的定义。对应于 Dataset1.SAV

中 Question_1 的 SPSS 值标签

DatasetA 包含带有 SPSS 值标签的变量 Question_A 1=同意 2=不确定 3=不同意。当此数据集在 Dataset1 之后导入时,SAS 会自动生成格式名称问题。对于 Question_A、,即使工作库已包含名为 QUESTION. 的格式。因此,这会覆盖 QUESTION 格式的定义。导入 Dataset1 时生成的。导入 DatasetA 后,格式 QUESTION 的定义。对应于 DatasetA.SAV

中 Question_A 的 SPSS 值标签

因此,当 Dataset1 和 DatasetA 都被导入时,变量 Question_1 和 Question_A 都具有分配给它们的格式名称 QUESTION - 以及格式 QUESTION 的定义。 SAS 工作文件夹中的对应于 DatasetA.SAV 中的 SPSS 值标签,而不是 Dataset1.SAV。因此,Question_1 将显示为 1=同意 2=不确定,即使变量值实际上意味着 1=是 2=否。

理想情况下,我希望这两个变量在导入步骤中自动生成不同的自定义格式名称。有什么办法可以做到这一点?或者,是否有任何其他方法可以防止发生此类覆盖?

谢谢。

防止文字覆盖的方法是使用 FMTLIB= 可选语句为每个正在读取的 SPSS 文件指向不同格式的目录。

proc import out=dataset1 replace 
   datafile="S:\folder\Dataset1.SAV" dbms=SAV 
; 
   fmtlib=work.fmtcat1;
run;
proc import out=dataset2 replace 
   datafile="S:\folder\Dataset2.SAV" dbms=SAV 
; 
   fmtlib=work.fmtcat2;
run;

稍后您可以重命名冲突的格式(并更改数据集中的附加格式以使用新名称)。

因此,如果成员名称和格式名称足够短,您应该能够通过附加两者来生成唯一的新名称(在两者之间添加一些内容以避免冲突)。所以这样的事情会重命名格式,更改附加到变量的格式名称并将格式重建到 WORK.FORMATS 目录中。

%macro sav_import(file,memname);
%if 0=%length(&memname) %then %let memname=%scan(&file,-2,\./);

proc import datafile=%sysfunc(quote(&file)) dbms=save
  out=&memname replace
; 
  fmtlib=work.&memname ;
run;

proc format lib=work.&memname cntlout=formats;
run;

data formats ;
  set formats end=eof;
  by fmtname type notsorted;
  oldname=fmtname;
  fmtname=catx('_',"&memname",oldname);
run;

proc contents data=&memname noprint out=contents;
run;

proc sql noprint;
  select distinct catx(' ',c.name,cats(f.fmtname,'.'))
    into :fmtlist separated by ' '
  from contents c inner join formats f
  on c.format = f.oldname
  ;
quit;

proc datasets nolist lib=work;
  modify &memname;
    format &fmtlist ;
  run;
quit;

proc format lib=work.formats cntlin=formats;
run;

%mend sav_import;

%sav_import(S:\folder\Dataset1.SAV);
%sav_import(S:\folder\Dataset2.SAV);