Как вытащить ширину и высоту из строки?

В нашей таблице товаров ширина и высота указаны непосредственно в описании товара.

Я пытаюсь разбить ширину и высоту на отдельные числовые столбцы, чтобы нам не приходилось возиться с длинными строками каждый раз, когда нам нужны данные о размере.

Однако проблема, с которой я столкнулся, заключается в том, что эти описания не стандартизированы. Большинство размеров правильно сохраняются как Ш" X В", но некоторые также могут быть Ш"ХВ", -Ш"хВ"-, а некоторые могут даже иметь третью двойную кавычку для закругления углов, длины и т. д.

Можно ли создать универсальную функцию, которая может извлекать ширину и высоту из всех типов форматов описания? Должен ли я разбить их на отдельные функции для каждого формата?

Константы:

  1. Все ширины и высоты являются целыми числами.
  2. За всеми значениями ширины и высоты следуют двойные кавычки.
  3. Между всеми значениями ширины и высоты стоит знак «X».

Переменные:

  1. Интервал и окружающие символы (не всегда пустое пространство до/после размеров)
  2. Количество двойных кавычек может быть больше двух.
  3. Могут быть одно-, двух- или трехзначными числами (1 х 1", 10 х 1", 100 х 1" и т. д.).

Образец данных:

Продукт Описание Ожидаемая ширина Ожидаемая высота 1000 HIP .100 Цифровой знак 12 x 18 дюймов 12 18 1001 HIP-080-36"X72"-Простой знак-RS 36 72 1002 DG3 .080 21 x 21 дюйм Знак 3 дюйма R 21 21 1003 HIP-080-36"X72"-Простой знак-RS 36 72 1004 DG3 FLO-125-100"x80"-ручная установка 100 80 1005 DG3 FLUOR Dbl 0,080 Выход 30 x 30 x 30 дюймов 30 30

Что я пробовал:

SELECT
    UPPER(REPLACE(
        REPLACE(
            RIGHT(
                LEFT(Description,CHARINDEX('"',Description,CHARINDEX('"',Description)+1)-1), 
            LEN(
                LEFT(Description,CHARINDEX('"',Description,CHARINDEX('"',Description)+1)-1)
                ) 
            - CHARINDEX('"', 
                LEFT(Description,CHARINDEX('"',Description,CHARINDEX('"',Description)+1)-1)
            ) + 3)
        , '"', '')
    , ' ','')) AS Result, Description

FROM HQMT
WHERE UPPER(Description) LIKE '%"%X%"%'

Результат:

Результат Описание 12X18 HIP .100 Цифровой знак 12 x 18 дюймов 36X72 HIP-080-36"X72"-Простой знак-RS 21X21 DG3 .080 21 x 21 дюйм Знак 3 дюйма R 36X72 HIP-080-36"X72"-Простой знак-RS 00X80 DG3 FLO-125-100"x80"-ручная установка 30X30 DG3 FLUOR Dbl 0,080 Выход 30 x 30 x 30 дюймов

Получив эти результаты, я планирую вытащить все символы слева от «X» для ширины и все символы справа от «X» для высоты. В основном это правильно, но ширина трех цифр обрезается. Есть идеи, как исправить/сделать динамичнее?

Честно говоря, это вряд ли будет задачей для SQL Server, и лучшим выбором будет язык с мощными инструментами манипулирования строками. Конечно, настоящее решение — исправить данные; это требует некоторой значительной нормализации.

Thom A 21.06.2024 17:00

Как вы хотите обрабатывать описания, содержащие одинарные или двойные кавычки и не связанные с измерениями? Например, знак «Большая Берта» 96 дюймов x 120 дюймов или строки с буквой X, например, знак Xavier 3 модели 2000 года.

Bart McEndree 21.06.2024 17:14

Это сложная задача даже для языков с надежными инструментами синтаксического анализа. См. stackoverflow.com/questions/57296129/…

Bart McEndree 21.06.2024 17:19

@BartMcEndree К счастью, их не существует, кавычки используются только для размеров в этой таблице. Строки с X и без кавычек уже отфильтровываются с помощью WHERE UPPER(Description) LIKE '%"%X%"%'.

Jack Morris 21.06.2024 17:21

Даже если я смогу обновить 80% из них с помощью этой функции, остальные я смогу ввести вручную. Это будет только одноразовое обновление и не будет проблемой в будущем.

Jack Morris 21.06.2024 17:26

Возможно, возьмите 4 символа слева и справа от X и удалите все нечисловые символы. stackoverflow.com/questions/18625548/…

Bart McEndree 21.06.2024 17:36

мои мысли обращаются к РЕГУЛЯРНЫМ ВЫРАЖЕНИЯМ....

Randy 28.06.2024 16:28
ReactJs | Supabase | Добавление данных в базу данных
ReactJs | Supabase | Добавление данных в базу данных
Это и есть ваш редактор таблиц в supabase.👇
Понимание Python и переход к SQL
Понимание Python и переход к SQL
Перед нами лабораторная работа по BloodOath:
1
7
70
3
Перейти к ответу Данный вопрос помечен как решенный

Ответы 3

Это просто вставит достаточно пробелов вокруг символов X и -, чтобы вы могли безопасно получить последние три символа, предшествующие каждой кавычке:

select * from T cross apply (
    select
        min(case when ordinal = 1 then cast(ltrim(right(value, 3)) as int) end),
        min(case when ordinal = 2 then cast(ltrim(right(value, 3)) as int) end)
    from string_split(
             replace(replace(replace(Description, '-', ' '), 'X', ' '), ' ', '   '),
             '"', 1) as s
) as dimensions(width, height)

Это предполагает, что ширина и высота всегда отображаются рядом с первыми двумя кавычками без пробела и что вы используете более новую версию SQL Server с выводом ordinal из string_split(). Этот случай можно было бы обработать, но поскольку он существует, это приведет к ошибке.

https://dbfiddle.uk/yfi5b4Tl

--Grab 4 chrs preceeding " and Adding another replace to remove dash
SELECT
    UPPER(
     REPLACE( 
      REPLACE(
        REPLACE(
            RIGHT(
                LEFT(Description,CHARINDEX('"',Description,CHARINDEX('"',Description)+1)-1), 
            LEN(
                LEFT(Description,CHARINDEX('"',Description,CHARINDEX('"',Description)+1)-1)
                ) 
            - CHARINDEX('"', 
                LEFT(Description,CHARINDEX('"',Description,CHARINDEX('"',Description)+1)-1)
            ) + 4)
        , '"', '')
    , ' ','')
    ,'-','')
              ) AS Result, Description

FROM HQMT
WHERE UPPER(Description) LIKE '%"%X%"%'

рабочий пример

Результат Описание 12X18 HIP .100 Цифровой знак 12 x 18 дюймов 36X72 HIP-080-36"X72"-Простой знак-RS 21X21 DG3 .080 21 x 21 дюйм Знак 3 дюйма R 36X72 HIP-080-36"X72"-Простой знак-RS 100X80 DG3 FLO-125-100"x80"-ручная установка 30X30 DG3 FLUOR Dbl 0,080 Выход 30 x 30 x 30 дюймов
Ответ принят как подходящий

Используйте ПЕРЕВОД, чтобы удалить все символы, кроме цифр и X (применяется к 4 символам перед ").

SELECT
    UPPER(
     REPLACE(TRANSLATE(
            RIGHT(
                LEFT(Description,CHARINDEX('"',Description,CHARINDEX('"',Description)+1)-1), 
            LEN(
                LEFT(Description,CHARINDEX('"',Description,CHARINDEX('"',Description)+1)-1)
                ) 
            - CHARINDEX('"', 
                LEFT(Description,CHARINDEX('"',Description,CHARINDEX('"',Description)+1)-1)
            ) + 4)
            , 'abcdefghijklmnopqrstuvwyz+()- ,#+"', '@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@'), '@', '')  
         ) 
  AS Result, Description

FROM HQMT
WHERE UPPER(Description) LIKE '%"%X%"%'

рабочий пример

Это близко, спасибо! Однако мне пришлось изменить все символы перевода на прописные и изменить каждую ссылку на описание на UPPER (Описание). Без этого он просто заменял строчные буквы. Он также не работает, если четвертый предшествующий символ является числом (HIP .125 6 x 12 дюймов получается как 56X12). Я просто вручную исключил эти записи.

Jack Morris 21.06.2024 18:42

Обязательно поместите это в пользовательскую функцию, чтобы каждый мог ее использовать :-)

MikeAinOz 21.06.2024 22:57

Другие вопросы по теме