Most Excel training tells you to 'clean your data first.' That’s backwards. You shouldn’t clean before transforming — you should transform *as* you clean. Every manual paste, find-and-replace, or column-split wastes time and introduces errors that won’t surface until Q3 reports go sideways.
The Problem
You get a raw export from your CRM — say, Salesforce or Zoho — and it looks like this:
| Raw_CRM_Export | Contact_Info | Deal_Size | Close_Date | Tags |
|---|---|---|---|---|
| Acme Corp (Active) | james.wong@acmecorp.com | +1 (415) 555-0192 | $125,000 | 2024-02-28 | Enterprise, Upsell, Renewal |
| Nexus Labs* | support@nexuslabs.io | $78,500 | 2024-03-15 | Beta, Pilot |
| Stellar Dynamics (Inactive) | contact@stellardyn.com | +44 20 7946 0958 | $210,300 | 2024-01-10 | Enterprise, Referral, Onboarding |
| Veridian Systems | sales@veridiansys.com | +1 (646) 555-0177 | $94,800 | 2024-04-02 | Renewal, Upsell |
| Orion Health (Pending) | hello@orionhealth.co.uk | $162,000 | 2024-05-11 | Enterprise, Contract Review |
Notice the symptoms? Company names have status tags in parentheses or asterisks. Contact info mixes email and phone — sometimes both, sometimes one. Deal size has dollar signs and commas. Dates are ISO-formatted but inconsistently typed. Tags are pipe-delimited or comma-separated. This isn’t ‘dirty’ data — it’s *structured differently*. And that’s where most people misdiagnose the issue.
The Solution
We’ll use Power Query — not formulas — because it’s repeatable, auditable, and handles variation gracefully. Here’s what you actually do:
- Select any cell in your table (say, A1), then press Alt → A → P — that’s the keyboard shortcut to open Power Query Editor with your range auto-detected.
- In Power Query, click the dropdown arrow next to Contact_Info → choose Split Column → By Delimiter. Select | as the delimiter, and choose Split at each occurrence. This gives you two new columns: Contact_Info.1 and Contact_Info.2.
- Rename those columns to Email and Phone. Then select the Email column → right-click → Transform → Lowercase. The beauty of this approach is that it applies to every row, even blanks — no IFERROR needed.
- Select Deal_Size → right-click → Transform → Replace Values. Type
$in 'Old value', leave 'New value' blank. Repeat for commas. Then right-click again → Change Type → Decimal Number. - For Company_Name, select the column → go to Transform → Format → Clean. That strips non-alphanumeric characters *except spaces*, removing
(Active),(Inactive), and*in one move.
Click Close & Load (Alt → F → C). Your transformed table lands in a new worksheet — clean, typed, and ready for PivotTables or charts.
| Company_Name | Phone | Deal_Size | Close_Date | Tag_1 | Tag_2 | Tag_3 | |
|---|---|---|---|---|---|---|---|
| Acme Corp | james.wong@acmecorp.com | +1 (415) 555-0192 | 125000 | 2024-02-28 | Enterprise | Upsell | Renewal |
| Nexus Labs | support@nexuslabs.io | 78500 | 2024-03-15 | Beta | Pilot | ||
| Stellar Dynamics | contact@stellardyn.com | +44 20 7946 0958 | 210300 | 2024-01-10 | Enterprise | Referral | Onboarding |
| Veridian Systems | sales@veridiansys.com | +1 (646) 555-0177 | 94800 | 2024-04-02 | Renewal | Upsell | |
| Orion Health | hello@orionhealth.co.uk | 162000 | 2024-05-11 | Enterprise | Contract Review |
What makes this elegant is that every step becomes a line in the Applied Steps pane — you can delete, reorder, or edit any transformation without breaking the rest. No more ‘I think I did the trim before the split…’ panic.
Going Further
You can extend this pipeline in powerful ways — all within Power Query:
- Dynamic tag splitting: Select the Tags column → right-click → Split Column → By Delimiter → choose Comma and check Advanced options → Split into rows. Now each tag lives on its own row — perfect for counting tag frequency with Group By.
- Date normalization: If Close_Date had mixed formats (some “Mar 15, 2024”, some “15/03/2024”), use Transform → Date → To Date. Power Query auto-detects locale and fixes it — no DATEVALUE gymnastics.
- Conditional company cleanup: Add a custom column with
=if Text.Contains([Company_Name], "(") then Text.BeforeDelimiter([Company_Name], "(") else [Company_Name]. It’s readable, debuggable, and faster than nested SUBSTITUTE formulas. - Reusing transformations: Once built, save your query as a Connection Only (no load), then reference it from other workbooks. Your cleaning logic stays versioned and shared — no more emailing ‘cleaned_v2_final_FINAL.xlsx’.
Here’s the counterintuitive tip: Don’t try to fix everything in one pass. Build small, testable steps — like isolating emails first, then validating them with Transform → Format → Email (which flags malformed addresses). Iteration beats perfection.
When NOT to Use This
Power Query shines for structured, repeating patterns — but it’s overkill or inappropriate in three cases:
- One-off edits on 5 rows: If you’re fixing typos in a 7-row internal budget sheet, just double-click and type. Power Query adds friction — not speed.
- Live-linked external data: If your source is a live SQL connection refreshing every minute, avoid Power Query’s default ‘Load’ behavior. Instead, use Edit Queries → Properties → Uncheck ‘Include in Refresh’ for transformation-only queries that feed static reports.
- Formulas dependent on intermediate states: If your dashboard uses =SUMIFS across partially cleaned columns (e.g., summing only rows where Company_Name contains “Corp”), don’t rely on Power Query output alone. Keep the original sheet intact and use XLOOKUP to pull clean values — preserving auditability.
Also: Never run Power Query on unprotected worksheets containing merged cells. It will either fail silently or return truncated results — especially in columns like Tags where merged rows break the row-column grid assumption.
Keyboard Shortcuts
| Action | Shortcut | Notes |
|---|---|---|
| Open Power Query Editor | Alt → A → P | Works from any cell in a table or range |
| Apply & Close | Alt → F → C | Saves and loads result to worksheet |
| Undo last step | Ctrl + Z | Works inside Power Query Editor too |
| Toggle formula bar | Ctrl + Shift + U | Critical when editing M code in Advanced Editor |