sqlcmd.net validated sql reference
advanced string-processing SQL Server PostgreSQL

Split A Delimited String Into Rows

Expand a comma-separated or delimited string into one row per element, turning a single cell into a proper set of rows.

Docker-validated Not currently validation-green

Split a comma-separated tags string into one row per tag

The string 'sql,database,query' contains three comma-separated values. After splitting, each becomes its own row. The result is sorted alphabetically — database, query, sql. SQL Server's STRING_SPLIT yields a table with a column named value. PostgreSQL's REGEXP_SPLIT_TO_TABLE yields an unnamed column, aliased here as item using the AS s(item) syntax. The MySQL/MariaDB JSON_TABLE workaround wraps the string in [", replaces , with ",", closes with "] to form valid JSON, then iterates over $[*] to produce one row per element.

SQL Server
Engine-specific syntax
Setup
CREATE TABLE posts (id INT, tags VARCHAR(200));

INSERT INTO
  posts (id, tags)
VALUES
  (1, 'sql,database,query');
SQL
SELECT
  TRIM(s.value) AS tag
FROM
  posts p CROSS APPLY STRING_SPLIT (p.tags, ',') s
WHERE
  p.id = 1
ORDER BY
  tag;
tag
database
query
sql
PostgreSQL
Engine-specific syntax
Setup
CREATE TABLE posts (id INT, tags VARCHAR(200));

INSERT INTO
  posts (id, tags)
VALUES
  (1, 'sql,database,query');
SQL
SELECT
  TRIM(s.item) AS tag
FROM
  posts p
  CROSS JOIN REGEXP_SPLIT_TO_TABLE (p.tags, ',') AS s (item)
WHERE
  p.id = 1
ORDER BY
  tag;
tag
database
query
sql

SQL Server uses STRING_SPLIT via CROSS APPLY. PostgreSQL uses REGEXP_SPLIT_TO_TABLE via CROSS JOIN. MySQL and MariaDB are unsupported natively; the shown workaround converts the string into a JSON array and expands it with JSON_TABLE. All four queries produce the same three rows sorted alphabetically.

Where this command helps.

  • normalizing a legacy column that stores comma-separated IDs or tags into individual rows
  • expanding a CSV input parameter into a table for use with IN or JOIN

What the command is doing.

Splitting a delimited string into rows is a common data-cleaning task when values arrive pre-joined in a single column or parameter. SQL Server provides STRING_SPLIT(string, delimiter) which returns a single-column table of values. PostgreSQL provides REGEXP_SPLIT_TO_TABLE(string, pattern) for regex-based splitting. MySQL and MariaDB lack a dedicated split function; the cleanest workaround uses JSON_TABLE to parse a JSON array formed by wrapping the string in brackets after replacing commas with ",".