Check whether a string is a palindrome
s == s[::-1] is the one-liner and allocates a reversed copy. The O(1)-space answer walks two pointers inwards, each skipping non-alphanumeric characters, comparing case-folded. It also short-circuits on the first mismatch, which the one-liner cannot.
Overview
The one-liner and its cost
s == s[::-1] is correct and reads well. It builds a full reversed copy first, so it is O(n) extra memory, and it always compares the entire string even when the first and last characters already disagree.
Cleaning first — clean = "".join(c.lower() for c in s if c.isalnum()) then comparing — is readable and costs a second full copy on top.
Step through it
What to watch
- Commas and spaces are skipped, not stripped into a new string.
- Both skip loops need the
lo < higuard. - A mismatch stops immediately — no need to check the rest.
Say this out loud
"Two pointers from both ends, skip anything that isn't alphanumeric, compare lowercased. O(n) time, O(1) space, and it bails on the first mismatch."