Il modo ideale sarebbe normalizzare i tuoi dati e dividi i due componenti della colonna in due colonne singole. Uno di tipo integer
, un text
.
Con la tabella corrente, puoi fare qualcosa come mostrato qui:
WITH x(t) AS (
VALUES
('10_asdaasda')
,('100_inkskabsjd')
,('11_kancaascjas')
,('45_aksndsialcn')
,('22_dsdaskjca')
,('100_skdnascbka')
)
SELECT t
FROM x
ORDER BY (substring(t, '^[0-9]+'))::int -- cast to integer
,substring(t, '[^0-9_].*$') -- works as text
Lo stesso substring()
le espressioni possono essere utilizzate per dividere la colonna.
Le espressioni regolari sono in qualche modo tolleranti agli errori:
-
La prima regex seleziona la stringa numerica più lunga da sinistra,
NULL
se non vengono trovate cifre, quindi esegui il cast suinteger
non puoi sbagliare. -
La seconda espressione regolare preleva il resto della stringa dal primo carattere che non è una cifra o '_'.
Se il carattere di sottolineatura non è comunque ambiguo come separatore, split_part()
è più veloce:
ORDER BY (split_part(t, '_', 1)::int
,split_part(t, '_', 2)
Rispondi per il tuo esempio
SELECT name
FROM nametable
ORDER BY (split_part(name, '_', 1)::int
,split_part(name, '_', 2)