一、问题抛出
在数据分析中我们有时候会遇到需要取出数组中最后一个值的方法
1)表xxx数据如下图所示:
2)现在需要取出字符串最后的"321" 和 "987"
二、方案探讨
1)反转字符串后,使用切割函数切割获取第一个值,然后再反转一下,代码如下:
select reverse(split(reverse(str),'_')[1]) from xxx;
性能分析:优点:写法简单!
缺点:此方法可以实现想要的效果,但是数据经过两次反转,查询性能比较低!
2)使用嵌套查询,思路是将字符串切割之后获取数组的大小,然后再减去1(因为数组下标从0开始)就是最后一个字符的索引,然后再第二层查询中使用此索引就能获取到最后一个字符串的内容
select split(str,'_')[str_index]
from
(SELECT str,(size(split(str,'_')) - 1) as str_index from xxx
)r;
性能分析:优点:写法复杂!
缺点:查询性能相较第一种写法性能好很多,特别是再数据量比较大的情景中!
3)编写UDF函数
此方法需要继承UDF类,重写evaluate()方法,这里先不讲!
优点:灵活性最高,耗时最长,适合无法使用sql中函数进行组合查询的情形,因为有些时候复杂逻辑在sql的能力范围之外,所以需要定制化开发!
总结:推荐第二种写法!
三、测试样例代码如下
1)select reverse(split(reverse('123_456_789_987'),'_')[1]);
2)select split(str,'_')[str_index]
from
(SELECT
'123_456_789_987' as str
,(size(split('123_456_789_987','_')) - 1) as str_index
union all
SELECT
'123_456_789_987_321' as str
,(size(split('123_456_789_987_321','_')) - 1) as str_index
)r;