Вот общее решение - с возможно более одной входной строки, так и с входами любой длины. Единственное предположение состоит в том, что ни одно слово не может быть более 15 символов, и что все между двумя пространствами считается словом. Если «слово» может содержать более 15 символов, решение можно адаптировать, но самому требованию нужно будет указать, какой желаемый результат будет в таком случае.
Я составляю две строки ввода в CTE (вверху) - это не часть решения, это просто для тестирования и иллюстрации. Я также написал это в простом SQL - для этого типа проблемы нет необходимости в PL/SQL-коде. Настройка обработки (вместо одной строки за раз) должна привести к значительно лучшему исполнению.
Подход заключается в том, чтобы идентифицировать местоположение всех пробелов (я добавляю и добавляю пространство для каждой строки тоже, поэтому мне не придется иметь дело с исключениями для первой и последней подстроки); то я решу в рекурсивном подзапросе, где должна начинаться каждая «максимальная» подстрока и где она должна заканчиваться; а затем выведение подстрок тривиально. Я использовал рекурсивный запрос, который должен работать в Oracle 11.1 (или 11.2 с синтаксисом, который я использовал, с именами столбцов в объявлениях CTE - его можно легко изменить для работы в 11.1). В Oracle 12 было бы проще переписать ту же идею, используя MATCH_RECOGINZE.
with
inputs (id, str) as (
select 101, 'I loooove my pet animal' from dual union all
select 102, '1992 was a great year for - make something up here as needed' from dual
),
positions (id, pos) as (
select id, instr(' ' || str || ' ', ' ', 1, level)
from inputs
connect by level <= length(str) - length(replace(str, ' ')) + 2
and prior id = id
and prior sys_guid() is not null
),
r (id, str, line_number, pos_from, pos_to) as (
select id, ' ' || str || ' ', 0, null, 1
from inputs
union all
select r.id, r.str, r.line_number + 1, r.pos_to,
(select max(pos)
from positions
where id = r.id and pos - r.pos_to between 1 and 16
)
from r
where pos_to is not null
)
select id, line_number, substr(str, pos_from + 1, pos_to - pos_from - 1) as line_text
from r
where line_number > 0 and pos_to is not null
order by id, line_number
;
Выход:
ID LINE_NUMBER LINE_TEXT
---- ----------- ---------------
101 1 I loooove my
101 2 pet animal
102 1 1992 was a
102 2 great year for
102 3 - make
102 4 something up
102 5 here as needed
7 rows selected.
что, если длина строки 50 Вы заканчиваете с двумя длиной 25 строки, это нормально? –
Нет, я не могу произвольно сломать слова. Мне не нужно сломать целое слово. Мне нужно разделить на две строки с полными словами. – Roshni
Так что, если строка '' Вы Supercalifragilisticexpialidocious '', где вы хотите разбить? Вы разделились на '' Вы - ''? –