CPT Codes: Complete Guide to Procedure Classification & Billing

Everything you need to know about CPT (Current Procedural Terminology) codes, database design, modifiers, RVUs, and billing integration.

What are CPT Codes?

CPT (Current Procedural Terminology) codes are a standardized set of medical codes maintained by the American Medical Association (AMA) used to describe medical, surgical, and diagnostic services. CPT codes are essential for billing, reimbursement, and healthcare data analytics.

Key Facts About CPT

  • Total Codes: 10,000+ procedure codes
  • Code Length: 5 digits (numeric)
  • Maintained By: American Medical Association (AMA)
  • Updates: Annual updates every January 1st
  • Copyright: AMA holds copyright, licensing required

CPT Code Categories

Category I - Permanent Codes

Most commonly used CPT codes for established procedures:

RangeCategoryExamples
99202-99499Evaluation & Management (E&M)Office visits, consultations, hospital care
00100-01999AnesthesiaAnesthesia services
10004-69990SurgerySurgical procedures by body system
70010-79999RadiologyX-rays, CT, MRI, ultrasound
80047-89398Pathology & LaboratoryLab tests, blood work
90281-99607MedicineImmunizations, dialysis, physical therapy

Category II - Performance Measurement Codes

Optional tracking codes for quality measurement (alphanumeric, ending in 'F'):

  • 3006F - Chest X-ray results documented
  • 4000F - Tobacco use assessed

Category III - Temporary Codes

Temporary codes for emerging procedures (alphanumeric, ending in 'T'):

  • 0075T - Transcatheter placement of extracranial vertebral artery stent

Database Schema for CPT Codes

CPT Master Table

CREATE TABLE cpt_codes (
  cpt_cd VARCHAR(10) PRIMARY KEY,
  
  -- Code Details
  cpt_desc VARCHAR(1000) NOT NULL,   -- Full description
  short_desc VARCHAR(100),            -- Abbreviated description
  
  -- Code Classification
  category VARCHAR(20),               -- Category I, II, III
  section VARCHAR(100),               -- E&M, Surgery, Radiology, etc.
  subsection VARCHAR(100),
  
  -- Code Type
  code_typ VARCHAR(20),               -- Primary, Add-on, Modifier 51 Exempt
  is_add_on BOOLEAN DEFAULT FALSE,   -- Add-on procedure
  is_bilateral BOOLEAN DEFAULT FALSE, -- Can be bilateral
  
  -- Reimbursement
  rvu_work DECIMAL(8,2),              -- Work RVU
  rvu_pe_nf DECIMAL(8,2),             -- Practice Expense (non-facility)
  rvu_pe_f DECIMAL(8,2),              -- Practice Expense (facility)
  rvu_mp DECIMAL(8,2),                -- Malpractice RVU
  rvu_total DECIMAL(8,2),             -- Total RVU
  
  -- Global Period
  global_days INT,                    -- Global period (0, 10, 90, etc.)
  
  -- Modifiers
  accepts_modifiers BOOLEAN DEFAULT TRUE,
  mod_51_exempt BOOLEAN DEFAULT FALSE, -- Multiple procedure modifier exempt
  
  -- Version Control
  eff_dt DATE NOT NULL,
  exp_dt DATE,
  version VARCHAR(10),                -- Annual version (e.g., '2024')
  
  -- Metadata
  last_upd_dt TIMESTAMP DEFAULT CURRENT_TIMESTAMP
);

-- Indexes
CREATE INDEX idx_cpt_section ON cpt_codes(section);
CREATE INDEX idx_cpt_desc ON cpt_codes USING gin(to_tsvector('english', cpt_desc));
CREATE INDEX idx_cpt_category ON cpt_codes(category);
CREATE INDEX idx_cpt_version ON cpt_codes(version, eff_dt);

Procedure Services Table

CREATE TABLE procedure_services (
  proc_svc_id VARCHAR(50) PRIMARY KEY,
  
  -- Patient & Encounter
  pt_id VARCHAR(50) NOT NULL,
  enc_id VARCHAR(50),
  clm_id VARCHAR(50),                 -- Associated claim
  
  -- Procedure
  cpt_cd VARCHAR(10) NOT NULL,
  proc_desc VARCHAR(1000),
  
  -- Modifiers (up to 4)
  mod_1 VARCHAR(2),                   -- Primary modifier
  mod_2 VARCHAR(2),                   -- Secondary modifier
  mod_3 VARCHAR(2),
  mod_4 VARCHAR(2),
  
  -- Service Details
  svc_dt DATE NOT NULL,               -- Date of service
  svc_qty INT DEFAULT 1,              -- Units/quantity
  svc_loc VARCHAR(2),                 -- Place of service
  
  -- Provider
  rendering_npi VARCHAR(10),          -- Performing provider
  facility_npi VARCHAR(10),           -- Facility
  
  -- Charges & Payments
  chrg_amt DECIMAL(10,2),             -- Billed amount
  alwd_amt DECIMAL(10,2),             -- Allowed amount
  pd_amt DECIMAL(10,2),               -- Paid amount
  
  -- Metadata
  crtd_dt TIMESTAMP DEFAULT CURRENT_TIMESTAMP,
  
  FOREIGN KEY (pt_id) REFERENCES patients(pt_id),
  FOREIGN KEY (cpt_cd) REFERENCES cpt_codes(cpt_cd)
);

-- Indexes
CREATE INDEX idx_proc_svc_pt ON procedure_services(pt_id);
CREATE INDEX idx_proc_svc_enc ON procedure_services(enc_id);
CREATE INDEX idx_proc_svc_cpt ON procedure_services(cpt_cd);
CREATE INDEX idx_proc_svc_dt ON procedure_services(svc_dt);
CREATE INDEX idx_proc_svc_npi ON procedure_services(rendering_npi);

CPT Modifiers

Modifiers are 2-digit codes appended to CPT codes to provide additional information:

Common CPT Modifiers

ModifierDescriptionUse Case
25Significant, separately identifiable E&ME&M service on same day as procedure
26Professional componentPhysician interpretation only
50Bilateral procedurePerformed on both sides
51Multiple proceduresMultiple procedures same session
59Distinct procedural serviceSeparate procedure
76Repeat procedure by same physicianSame day repeat
LT/RTLeft/Right sideSpecify laterality

Common CPT Code Abbreviations

AbbreviationFull TermDescription
cpt_cdCPT codeProcedure code
proc_cdprocedure codeGeneral procedure code field
modmodifierCPT modifier code
rvurelative value unitPayment calculation unit
posplace of serviceService location code
tostype of serviceService type classification

Relative Value Units (RVUs)

RVUs are used to calculate Medicare reimbursement. Each CPT code has associated RVU values:

RVU Components

  • Work RVU - Physician work, time, skill, intensity
  • Practice Expense RVU - Overhead costs (staff, supplies, equipment)
  • Malpractice RVU - Professional liability insurance

Reimbursement Calculation

-- Medicare payment formula
Payment = (Work RVU + PE RVU + MP RVU) × Conversion Factor × Geographic Adjustment

-- SQL calculation example
SELECT 
  cpt_cd,
  cpt_desc,
  rvu_total,
  (rvu_total * 33.8872) as medicare_payment_2024
FROM cpt_codes
WHERE cpt_cd = '99213';  -- Office visit, established patient

-- Result: ~$100 for typical office visit

Common E&M Codes (Evaluation & Management)

Office Visits - New Patient

  • 99202 - Level 2 (straightforward, 15-29 min)
  • 99203 - Level 3 (low complexity, 30-44 min)
  • 99204 - Level 4 (moderate complexity, 45-59 min)
  • 99205 - Level 5 (high complexity, 60-74 min)

Office Visits - Established Patient

  • 99211 - Level 1 (minimal, may not require physician)
  • 99212 - Level 2 (straightforward, 10-19 min)
  • 99213 - Level 3 (low complexity, 20-29 min)
  • 99214 - Level 4 (moderate complexity, 30-39 min)
  • 99215 - Level 5 (high complexity, 40-54 min)

CPT Lookup Queries

-- Search by keyword
SELECT cpt_cd, cpt_desc, rvu_total
FROM cpt_codes
WHERE to_tsvector('english', cpt_desc) @@ to_tsquery('english', 'knee & arthroscopy')
ORDER BY cpt_cd;

-- Find all E&M office visit codes
SELECT cpt_cd, cpt_desc, rvu_total
FROM cpt_codes
WHERE cpt_cd BETWEEN '99202' AND '99215'
ORDER BY cpt_cd;

-- Most frequently billed procedures
SELECT 
  ps.cpt_cd,
  c.cpt_desc,
  COUNT(*) as proc_cnt,
  SUM(ps.chrg_amt) as total_charges,
  AVG(ps.pd_amt) as avg_payment
FROM procedure_services ps
JOIN cpt_codes c ON ps.cpt_cd = c.cpt_cd
WHERE ps.svc_dt >= CURRENT_DATE - INTERVAL '1 year'
GROUP BY ps.cpt_cd, c.cpt_desc
ORDER BY proc_cnt DESC
LIMIT 100;

-- Provider productivity by RVU
SELECT 
  rendering_npi,
  COUNT(DISTINCT pt_id) as patient_cnt,
  COUNT(*) as proc_cnt,
  SUM(c.rvu_total) as total_rvus
FROM procedure_services ps
JOIN cpt_codes c ON ps.cpt_cd = c.cpt_cd
WHERE svc_dt BETWEEN '2024-01-01' AND '2024-12-31'
GROUP BY rendering_npi
ORDER BY total_rvus DESC;

Integration with Claims

EDI 837 Professional Claims

CPT codes appear in the SV1 segment:

  • SV1*HC:99213*100.00*UN*1***1
  • HC = CPT/HCPCS qualifier
  • 99213 = CPT code
  • 100.00 = Charge amount
  • UN = Unit
  • 1 = Quantity

Modifiers in Claims

-- Claims with modifiers
CREATE TABLE claim_procedures (
  clm_proc_id VARCHAR(50) PRIMARY KEY,
  
  clm_id VARCHAR(50) NOT NULL,
  line_nbr INT NOT NULL,
  
  cpt_cd VARCHAR(10) NOT NULL,
  mod_1 VARCHAR(2),
  mod_2 VARCHAR(2),
  mod_3 VARCHAR(2),
  mod_4 VARCHAR(2),
  
  svc_dt DATE NOT NULL,
  svc_qty INT DEFAULT 1,
  
  chrg_amt DECIMAL(10,2),
  alwd_amt DECIMAL(10,2),
  pd_amt DECIMAL(10,2),
  
  FOREIGN KEY (clm_id) REFERENCES claims(clm_id),
  FOREIGN KEY (cpt_cd) REFERENCES cpt_codes(cpt_cd)
);

Best Practices

Coding Accuracy

  • ✅ Use most specific CPT code available
  • ✅ Append appropriate modifiers
  • ✅ Verify code is active for date of service
  • ✅ Check for bundled procedures (CCI edits)
  • ✅ Document medical necessity

Data Quality

  • ✅ Validate CPT codes against master table
  • ✅ Ensure modifier combinations are valid
  • ✅ Verify units/quantity are appropriate
  • ✅ Check place of service codes

Annual Updates

  • ✅ Download updated CPT files every January 1st
  • ✅ Update RVU values from CMS fee schedule
  • ✅ Test new/deleted/revised codes
  • ✅ Communicate changes to providers and billers

CPT vs HCPCS

HCPCS (Healthcare Common Procedure Coding System) includes CPT plus additional codes:

  • Level I HCPCS = CPT codes (maintained by AMA)
  • Level II HCPCS = Non-physician services (maintained by CMS)
    • A codes - Supplies, DME
    • J codes - Drugs
    • Q codes - Temporary codes

Resources

Official CPT Resources