1

I have a column of data that looks like this:

58,0:102,56.00
52,0:58,68
58,110
57,440.00
52,0:58,0:106,6105.95

I need to extract the character before the last delimiter (',').

Using the data above, I want to get:

102
58
58
57
106
1
  • 1
    I need to extract the character .. Your desired result lists numbers, not characters. Please clarify. Define what you consider separating characters besides the mentioned ','. Commented Aug 3, 2019 at 4:24

5 Answers 5

1

Might be done with a regular expression in substring(). If you want:
the longest string of only digits before the last comma:

substring(data, '(\d+)\,[^,]*$')

Or you may want:
the string before the last comma (',') that's delimited at the start either by a colon (':') or the start of the string.
Could be another regexp:

substring(data, '([^:]*)\,[^,]*$')

Or this:

reverse(split_part(split_part(reverse(data), ',', 2), ':', 1))

More verbose but typically much faster than a (expensive) regular expression.

db<>fiddle here

Sign up to request clarification or add additional context in comments.

Comments

0

Can't promise this is the best way to do it, but it is a way to do it:

with splits as (
  select string_to_array(bar, ',') as bar_array
  from foo
),
second_to_last as (
  select
    bar_array[cardinality(bar_array)-1] as field
  from splits
)
select
  field,
  case
    when field like '%:%' then split_part (field, ':', 2)
    else field
  end as last_item
from second_to_last

I went a little overkill on the CTEs, but that was to expose the logic a little better.

Comments

0

With a CTE that removes everything after the last comma and then splits the rest into an array:

with cte as (
  select
    regexp_split_to_array(
      replace(left(col, length(col) - position(',' in reverse(col))), ':', ','),
      ','
    ) arr                                             
  from tablename  
)  
select arr[array_upper(arr, 1)] from cte

See the demo.
Results:

| result |
| ------ |
| 102    |
| 58     |
| 58     |
| 57     |
| 106    |

Comments

0

The following treats the source string as an "array of arrays". It seems each data element can be defined as S(x,y) and the overall string as S1:S2:...Sn. The task then becomes to extract x from Sn.

with as_array as 
     ( select string_to_array(S[n], ',') Sn 
         from (select string_to_array(col,':') S
                    , length(regexp_replace(col, '[^:]','','g'))+1  n 
                 from tablename 
              ) t
     )
select Sn[array_length(Sn,1)-1] from as_array

The above extends S(x,y) to S(a,b,...,x,y) the task remains to extracting x from Sn. If it is the case that all original sub-strings S are formatted S(x,y) then the last select reduces to select Sn[1]

Comments

-1

This worked for me, I just needed the last field. select substring('abc:def:hij:kef', ':[^:]*$');

substring

:kef (1 row)

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.