ποΈ SQL Β· Topic 9 of 20
String Functions β SQL Questions with Answers
30 practice questions on String Functions, each with the correct answer and a clear explanation of why it is right. Read through them as revision notes, or take this topic as an interactive quiz to test yourself.
3 easy Β· 17 medium Β· 10 hard Β· Part of SQL: Databases from basics to window functions - 20 topics.
Medium questions (17)
Q4. medium
What does TRIM(' hello ') return?
SELECT TRIM(' hello '); -- 'hello'
- A 'hello' - leading and trailing spaces removed
- B ' hello '
- C 'hello '
- D 'h e l l o'
Answer: A β 'hello' - leading and trailing spaces removed
TRIM removes whitespace from both ends. LTRIM removes only the left side and RTRIM only the right. Spaces inside the string are untouched.
TRIMLTRIMRTRIM
Q5. medium
What does SUBSTRING('database', 1, 4) return?
SELECT SUBSTRING('database', 1, 4); -- 'data'
SELECT SUBSTRING('database', 5, 4); -- 'base'
- A 'data' - 4 characters starting at position 1
- B 'base'
- C 'atab'
- D 'databa'
Answer: A β 'data' - 4 characters starting at position 1
SUBSTRING(string, start, length) extracts a portion. Note SQL positions are usually 1-based, not 0-based like most programming languages.
SUBSTRINGSUBSTR
Q7. medium
What does REPLACE('2026-07-04', '-', '/') return?
SELECT REPLACE(phone, '-', ''); -- strip dashes
- A '2026/07/04' - every '-' replaced with '/'
- B '20260704'
- C Only the first '-' replaced
- D An error
Answer: A β '2026/07/04' - every '-' replaced with '/'
REPLACE swaps EVERY occurrence of the search text, not just the first. It is commonly used for reformatting and cleaning data.
REPLACE
Q8. medium
How do you find the position of a substring?
SELECT SUBSTRING(email, 1, POSITION('@' IN email) - 1) AS username;
- A POSITION('@' IN email) or CHARINDEX / INSTR depending on the database
- B FIND('@', email)
- C INDEX(email, '@')
- D SEARCH(email, '@')
Answer: A β POSITION('@' IN email) or CHARINDEX / INSTR depending on the database
POSITION is standard SQL; SQL Server uses CHARINDEX('@', email) and MySQL/Oracle use INSTR(email, '@'). All return 1-based positions, or 0 when not found.
POSITIONCHARINDEXINSTR
Q10. medium
What do LEFT('hello', 3) and RIGHT('hello', 2) return?
SELECT LEFT(code, 2) AS prefix, RIGHT(code, 4) AS suffix FROM items;
- A 'hel' and 'lo'
- B 'llo' and 'he'
- C 'hel' and 'll'
- D 'lo' and 'hel'
Answer: A β 'hel' and 'lo'
LEFT takes characters from the start, RIGHT from the end. They are shorthand for common SUBSTRING cases. (Oracle lacks them; use SUBSTR instead.)
LEFTRIGHT
Q11. medium
What does REVERSE('SQL') return?
- A 'LQS'
- B 'SQL'
- C 'QLS'
- D An error
Answer: A β 'LQS'
REVERSE flips the character order. It is occasionally useful for extracting text after the LAST occurrence of a character (reverse, find, reverse again).
REVERSE
Q13. medium
What does CONCAT_WS(', ', city, state, country) do?
SELECT CONCAT_WS(', ', city, state, country) AS location FROM addresses;
- A Joins with a separator AND skips NULL arguments - no doubled separators
- B Joins without any separator
- C Only joins two strings
- D Reverses the string
Answer: A β Joins with a separator AND skips NULL arguments - no doubled separators
CONCAT_WS ('with separator') is ideal for addresses: it puts ', ' between values and gracefully skips missing fields instead of leaving ', , '.
CONCAT_WSNULL
Q14. medium
How do you pad a number to a fixed width, like '007'?
SELECT LPAD(CAST(id AS CHAR), 5, '0') FROM invoices; -- 00042
- A LPAD('7', 3, '0')
- B PAD('7', 3)
- C FILL('7', '0', 3)
- D FORMAT('7', 3)
Answer: A β LPAD('7', 3, '0')
LPAD pads on the left to reach a target length; RPAD pads on the right. Useful for invoice numbers and codes. (SQL Server lacks LPAD - use RIGHT('000' + val, 3).)
LPADRPAD
Q16. medium
What does SUBSTRING('database' FROM 5) return (no length given)?
- A 'base' - from position 5 to the end
- B 'data'
- C 'd'
- D An error
Answer: A β 'base' - from position 5 to the end
Omitting the length extracts everything from the start position onward. This is handy when you know where to start but not how long the remainder is.
SUBSTRING
Q17. medium
How do you capitalise the first letter of each word (title case)?
- A INITCAP('hello world') in PostgreSQL/Oracle returns 'Hello World'
- B UPPER() does it automatically
- C TITLE('hello world')
- D CAPITALIZE()
Answer: A β INITCAP('hello world') in PostgreSQL/Oracle returns 'Hello World'
INITCAP handles title case in PostgreSQL and Oracle. MySQL and SQL Server lack it, so you build it with SUBSTRING + UPPER or a custom function.
INITCAPDialects
Q19. medium
How do you split a full name into first and last using space position?
SELECT SPLIT_PART(name, ' ', 1) AS first_name; -- PostgreSQL
- A Use POSITION(' ' IN name) with SUBSTRING for each part
- B SPLIT(name, ' ')
- C name.split(' ')
- D EXPLODE(name)
Answer: A β Use POSITION(' ' IN name) with SUBSTRING for each part
Most databases lack a simple SPLIT into columns. You locate the delimiter and slice around it. (PostgreSQL has SPLIT_PART(name, ' ', 1) which is much cleaner.)
SPLIT_PARTPOSITION
Q21. medium
How do you count occurrences of a character in a string?
SELECT LENGTH(tags) - LENGTH(REPLACE(tags, ',', '')) + 1 AS tag_count;
- A LENGTH(str) - LENGTH(REPLACE(str, 'x', '')) gives the count of 'x'
- B COUNT('x', str)
- C OCCURRENCES(str, 'x')
- D There is no way
Answer: A β LENGTH(str) - LENGTH(REPLACE(str, 'x', '')) gives the count of 'x'
A clever idiom: remove the character, and the drop in length equals how many were removed. Works in any database with LENGTH and REPLACE.
LENGTHREPLACETricks
Q22. medium
What does the || operator do in PostgreSQL?
- A String concatenation - 'Hello' || ' World' gives 'Hello World'
- B Logical OR
- C Bitwise OR
- D Absolute value
Answer: A β String concatenation - 'Hello' || ' World' gives 'Hello World'
In standard SQL, || concatenates strings (it is NOT logical OR - that is the keyword OR). Remember it returns NULL if either side is NULL.
ConcatenationOperators
Q24. medium
What does FORMAT or TO_CHAR help with?
- A Formatting numbers and dates as strings - e.g. adding commas or currency symbols
- B Only uppercasing
- C Splitting strings
- D Counting rows
Answer: A β Formatting numbers and dates as strings - e.g. adding commas or currency symbols
TO_CHAR(1234567, '9,999,999') gives '1,234,567' in PostgreSQL/Oracle; SQL Server uses FORMAT(). Ideally do display formatting in the application, not the query.
TO_CHARFORMAT
Q25. medium
How do you remove all spaces from a string?
- A REPLACE(str, ' ', '')
- B TRIM(str)
- C DELETE(str, ' ')
- D STRIP(str)
Answer: A β REPLACE(str, ' ', '')
TRIM only removes spaces at the ENDS. REPLACE with an empty string removes them everywhere - useful for normalising phone numbers or codes.
REPLACETRIM
Q27. medium
How do you mask a value like a credit card, showing only the last 4?
- A CONCAT('****-****-****-', RIGHT(card, 4))
- B HIDE(card)
- C MASK(card, 4)
- D card - 4
Answer: A β CONCAT('****-****-****-', RIGHT(card, 4))
Combine a literal mask with RIGHT to reveal only the tail. This is a common display transformation - though real card numbers should never be stored in plain text.
RIGHTCONCATSecurity
Q29. medium
How do you compare strings ignoring case portably?
- A LOWER(a) = LOWER(b) - normalise both sides
- B a == b
- C a EQUALS b
- D IGNORECASE(a, b)
Answer: A β LOWER(a) = LOWER(b) - normalise both sides
Since collation defaults differ between databases, normalising with LOWER (or UPPER) guarantees consistent case-insensitive comparison - at the cost of possibly bypassing an index.
LOWERCollation
Hard questions (10)
Q6. hard
In SQL, string positions typically start at what number?
- A 1 - SQL is 1-indexed, unlike most programming languages
- B 0
- C -1
- D It varies randomly
Answer: A β 1 - SQL is 1-indexed, unlike most programming languages
SUBSTRING('abc', 1, 1) returns 'a'. This 1-based indexing catches out developers used to Python or JavaScript, where the first character is at index 0.
IndexingSUBSTRING
Q9. hard
How would you extract the username (before @) from an email?
- A SUBSTRING(email, 1, POSITION('@' IN email) - 1)
- B LEFT(email, '@')
- C SPLIT(email, '@')
- D email BEFORE '@'
Answer: A β SUBSTRING(email, 1, POSITION('@' IN email) - 1)
Find the @ position, then take everything before it. The -1 excludes the @ itself. Combining POSITION with SUBSTRING is a common text-parsing pattern.
SUBSTRINGPOSITION
Q12. hard
What does CONCAT('Hi', NULL, 'there') return in MySQL vs the || operator?
-- safe with ||:
first || COALESCE(' ' || middle, '') || ' ' || last
- A CONCAT ignores NULL and returns 'Hithere'; || in standard SQL would return NULL
- B Both return NULL
- C Both return 'Hithere'
- D Both error
Answer: A β CONCAT ignores NULL and returns 'Hithere'; || in standard SQL would return NULL
CONCAT() in MySQL and SQL Server treats NULL as an empty string, but the standard || operator (and Oracle) returns NULL if any operand is NULL. This difference causes real bugs when building names.
CONCATNULLDialects
Q15. hard
Why might WHERE UPPER(name) = 'ANA' be slow on a large table?
- A Wrapping the column in a function prevents the index on name from being used
- B UPPER is always slow
- C It returns wrong results
- D It is not slow
Answer: A β Wrapping the column in a function prevents the index on name from being used
The database must compute UPPER for every row. Solutions: a case-insensitive collation, a functional index on UPPER(name), or a generated column storing the uppercased value.
SargabilityIndexesPerformance
Q18. hard
What does TRIM(BOTH 'x' FROM 'xxhelloxx') return?
- A 'hello' - TRIM can remove characters other than spaces
- B 'xxhelloxx'
- C 'helloxx'
- D An error
Answer: A β 'hello' - TRIM can remove characters other than spaces
Standard TRIM accepts a character set and a direction (BOTH, LEADING, TRAILING). Not every database supports the full syntax, but it is powerful for cleaning delimited data.
TRIMStandard SQL
Q20. hard
What does SPLIT_PART('a,b,c', ',', 2) return in PostgreSQL?
- A 'b' - the 2nd part when split on comma
- B 'a'
- C 'c'
- D 'a,b'
Answer: A β 'b' - the 2nd part when split on comma
SPLIT_PART extracts one field from delimited text by position (1-based). It is the neat way to parse CSV-like values stored in a single column.
SPLIT_PARTParsing
Q23. hard
Which finds rows where a name contains only letters (basic validation)?
WHERE name ~ '^[A-Za-z ]+$'; -- letters and spaces only
- A WHERE name ~ '^[A-Za-z]+$' (PostgreSQL regex) or a LIKE/pattern check
- B WHERE name = LETTERS
- C WHERE ISALPHA(name)
- D WHERE name LIKE '%[0-9]%'
Answer: A β WHERE name ~ '^[A-Za-z]+$' (PostgreSQL regex) or a LIKE/pattern check
PostgreSQL's ~ operator applies a regular expression. MySQL uses REGEXP, and SQL Server uses LIKE with character ranges. Regex is the flexible tool for text validation.
RegexValidation
Q26. hard
Why can trailing spaces in CHAR columns cause comparison surprises?
- A CHAR pads with spaces, so 'ab' stored in CHAR(5) is really 'ab ' - comparisons may ignore or include the padding depending on rules
- B CHAR never pads
- C Spaces are always removed
- D It never causes issues
Answer: A β CHAR pads with spaces, so 'ab' stored in CHAR(5) is really 'ab ' - comparisons may ignore or include the padding depending on rules
Standard SQL comparison ignores trailing spaces for equality, but LENGTH and LIKE may not. VARCHAR avoids the whole problem by storing exactly what you insert.
CHARTrailing spaces
Q28. hard
What does REGEXP_REPLACE do?
SELECT REGEXP_REPLACE(phone, '[^0-9]', '', 'g') AS digits FROM contacts;
- A Replaces text matching a regular expression pattern - more powerful than plain REPLACE
- B Only replaces the first character
- C Reverses a string
- D Counts matches
Answer: A β Replaces text matching a regular expression pattern - more powerful than plain REPLACE
REGEXP_REPLACE(phone, '[^0-9]', '', 'g') strips every non-digit in one call. Available in PostgreSQL, Oracle and MySQL 8+.
REGEXP_REPLACERegex
Q30. hard
Which query finds names with leading or trailing spaces (a data-quality check)?
- A WHERE name <> TRIM(name)
- B WHERE name LIKE ' %'
- C WHERE LENGTH(name) > 0
- D WHERE name IS NULL
Answer: A β WHERE name <> TRIM(name)
If a value differs from its trimmed version, it has stray spaces. This one-line check finds messy data that would otherwise break joins and grouping. (Option B only catches leading spaces.)
TRIMData quality