################################################################################ # objective - the pccc_v2.0 in medicalcoder should reproduce the results from # pccc version 1.0.6 _almost_ identically. # # There are a few differences. The reason for this difference is that the old # pccc package only mapped to conditions and did not map subconditions. this # creates a problem with a few codes that were not documented but in the # software. Those will be noted in this script. library(medicalcoder) # get the ICD codes from the medicalcoder package and add a code_id column icd_codes <- get_icd_codes() icd_codes[["code_id"]] <- seq_len(nrow(icd_codes)) # pccc_1.0.6 requires the input to be in a wide format and can only apply logic # for ICD-9 or ICD-10 in one call. Split the codes into the four sets ICD-9-CM, # ICD-9-PCS, ICD-10-CM, and ICD-10-PCS. Apply pccc::ccc to each and bind the # results so we know when ICD codes map to which conditions. # # The following code generates the output object which is saved in the test # directory such that the pccc_v1.0.6 package is not needed in the SUGGESTS # section of the DESCRIPTION file. ### library(pccc) ### stopifnot(packageVersion("pccc") == "1.0.6") ### ### oldpccc <- rbind( ### pccc::ccc( ### data = icd_codes[icd_codes$icdv == 9 & icd_codes$dx == 1, c("code_id", "code")], ### id = code_id, ### dx_cols = "code", ### icdv = 9 ### ) ### , ### pccc::ccc( ### data = icd_codes[icd_codes$icdv == 9 & icd_codes$dx == 0, c("code_id", "code")], ### id = code_id, ### pc_cols = "code", ### icdv = 9 ### ) ### , ### pccc::ccc( ### data = icd_codes[icd_codes$icdv == 10 & icd_codes$dx == 1, c("code_id", "code")], ### id = code_id, ### dx_cols = "code", ### icdv = 10 ### ) ### , ### pccc::ccc( ### data = icd_codes[icd_codes$icdv == 10 & icd_codes$dx == 0, c("code_id", "code")], ### id = code_id, ### pc_cols = "code", ### icdv = 10 ### ) ### ) ### ### saveRDS(oldpccc, file = "results_pccc_1.0.6.rds") oldpccc <- readRDS(file = "results_pccc_1.0.6.rds") newpccc <- medicalcoder::comorbidities( data = icd_codes , icd.codes = "full_code" , id.vars = "code_id" , icdv.var = "icdv" , icdv = NULL , dx.var = "dx" , dx = NULL , poa = 1 , poa.var = NULL , age.var = NULL , primarydx = NULL , primarydx.var = NULL , flag.method = "current" , full.codes = TRUE , compact.codes = TRUE , method = "pccc_v2.0" ) old_vs_mdcr <- merge( x = oldpccc, y = newpccc, all = TRUE, by = "code_id", suffixes = c("_old", "_mdcr") ) old_vs_mdcr <- merge(x = old_vs_mdcr, y = icd_codes[, c("code_id", "icdv", "dx", "full_code")], all = TRUE, by = "code_id" ) stopifnot(!any(is.na(old_vs_mdcr))) # expect no difference in the following conditions: # neuromusc # cvd # respiratory # renal # gi # hemato_immu # metabolic # congeni_genetic # malignancy # neonatal stopifnot( with(old_vs_mdcr, all(neuromusc_old == neuromusc_mdcr)), with(old_vs_mdcr, all(cvd_old == cvd_mdcr)), with(old_vs_mdcr, all(respiratory_old == respiratory_mdcr)), with(old_vs_mdcr, all(renal_old == renal_mdcr)), with(old_vs_mdcr, all(gi_old == gi_mdcr)), with(old_vs_mdcr, all(hemato_immu_old == hemato_immu_mdcr)), with(old_vs_mdcr, all(metabolic_old == metabolic_mdcr)), with(old_vs_mdcr, all(congeni_genetic_old == congeni_genetic_mdcr)), with(old_vs_mdcr, all(malignancy_old == malignancy_mdcr)), with(old_vs_mdcr, all(neonatal_old == neonatal_mdcr)) ) # we expect there is no difference in the ccc_flag (old) vs cmrb_flag (new) stopifnot( with(old_vs_mdcr, all(ccc_flag == cmrb_flag)) ) # # we _do_ expect differences in the tech_dep flag # # ICD-9-CM 349.1 - not in the v2 document, but in the software for neuromusc # only. This raises an problem that the subcondtion is not defined. To allow # for the methods in medicalcoder to work, a non missing subcondition is needed. # device and technology use was seems appropriate # # ICD-9-CM V56 - same, not in v2 documents, in the software # # ICD-10-CM Z49 - same, not in v2 documents, in the software # # ICD-9-PCS 86.06 - this is in the document as metabolic (devices) but is only # listed under metabolic in the software. Again, becuase of the use of the # subconditions in the implimentation in medicalcoder the corrected mapping is # needed in medicalcoder and thus the difference. # # ICD-9-CM V45.85 - same as ICD-9-PCS 86.06 # # ICD-9-CM V53.3 - great, this is a header code using in cvd, the assignable # codes, V53.31, V53.32, V53.39 are explicitly mapped to tech dep. The result, # the V53.3 needs to also have a tech dep flag # subset(get_icd_codes(), grepl("^V53\\.3", full_code) & icdv == 9) # # ICD-9-CM V53.91 "Fitting and adjustment of insulin pump" # This is listed in the documentation as metabolic (devices) by has been # implanted in R as metabolic (transplant). One major issue with this error is # that there are no codes for metabolic (transplant). It doesn't make since to # retain this error so, method=pccc_v2.0 will differ from the R package # pccc_1.0.6 for this code. # # subset(get_icd_codes(with.descriptions = TRUE), grepl("^V53\\.9", full_code) & icdv == 9) # # ICD-9-CM V65, and specifically V65.46 (encounter for insulin pump training), # is not in the documentation but is in the R pccc_v1.0.6 implimentation as # metabolic. The device flag as been added to this code. # subset(get_icd_codes(with.descriptions = TRUE), grepl("^V65\\.4", full_code) & icdv == 9) mismatch_tech_dep <- old_vs_mdcr[old_vs_mdcr$tech_dep != old_vs_mdcr$any_tech_dep, ] stopifnot(nrow(mismatch_tech_dep) == 18L) stopifnot( isTRUE(identical(sort(mismatch_tech_dep$full_code), c("349.1", "86.06", "V45.85", "V53.3", "V53.91", "V56", "V56.0", "V56.1", "V56.2", "V56.3", "V56.31", "V56.32", "V56.8", "V65.46", "Z49.01", "Z49.02", "Z49.31", "Z49.32") ) ) ) # we expect there are some difference in the transplant flag # # ICD-9-PCS 37.52 -- documented as cvd (device) implimented as cvd and # transplant. #subset(get_pccc_codes(), grepl("^37\\.52", full_code)) #subset(get_icd_codes(with.descriptions = TRUE), grepl("^37\\.52", full_code)) # ICD-9-CM V42.0 # documented as renal (transplant) # missing from the transplant set in the pccc_1.0.6/src/pccc.cpp #subset(get_pccc_codes(), grepl("^V42\\.0", full_code)) #subset(get_icd_codes(with.descriptions = TRUE), grepl("^V42\\.0", full_code) & icdv == 9) # ICD-10-CM Z94 # specifically Z94.1, Z94.2, Z94.4, Z94.81, Z94.82, Z94.83, Z94.84 # All documented as subcondition transplant but are missing from the transplant # set in the pccc_1.0.6/srs/pccc.cpp # #subset(get_pccc_codes(), grepl("^Z94", full_code)) #subset(get_icd_codes(with.descriptions = TRUE), grepl("^Z94", full_code) & icdv == 10) # mismatch_transplant <- old_vs_mdcr[old_vs_mdcr$transplant != old_vs_mdcr$any_transplant, ] mismatch_transplant[, c("full_code", "transplant", "any_transplant")] stopifnot(nrow(mismatch_transplant) == 15L) stopifnot( isTRUE(identical(sort(unique(mismatch_transplant$full_code)), c("37.52", "37.53", "37.54", "37.55", "V42.0", "Z94.1", "Z94.2", "Z94.4", "Z94.81", "Z94.82", "Z94.83", "Z94.84") ) ) ) ################################################################################ # End of File # ################################################################################