Я в основном скопировал это из этого ответа: https://stackoverflow.com/a/16667778/9101689
Он использует patindex для определения позиции числовых значений и подстрок из фактического значения. Мы берем эту подстроку и используем функцию ВЛЕВО, чтобы обрезать все вправо и приводить это значение как int к порядку.
declare @d table (drug_id nvarchar(max))
insert into @d values ('A-1'),('A-10A'),('A-11'),('A-2'),('A-20A'),('A-21'),('A-22'),('A-3'),('A-30'),('A-31')
SELECT *
FROM (
SELECT ORD_subsrt = SUBSTRING(drug_id, ORD_pos, LEN(drug_id)), *
FROM (
SELECT ORD_pos = PATINDEX('%[0-9]%', drug_id), *
FROM @d
) d
) t
Order by cast(LEFT(ORD_subsrt, PATINDEX('%[^0-9]%', ORD_subsrt + 't') - 1) as int)
Значение t добавляется, так что patindex "% [^ 0-9]%" вернет ненулевое значение в случае, если в поле drug_id нет нечислового суффикса.
или менее читаемый:
SELECT *
From @d
Order by cast(LEFT(SUBSTRING(drug_id, PATINDEX('%[0-9]%', drug_id), LEN(drug_id)), PATINDEX('%[^0-9]%', SUBSTRING(drug_id, PATINDEX('%[0-9]%', drug_id), LEN(drug_id)) + 't') - 1) as int)
Это не будет работать должным образом, если у вас есть значение типа «A2-10A» (или что-либо с более чем одним числовым значением).