我如何使用sql在一行中仅返回一部分值

时间:2018-12-28 17:23:33

标签: sql sql-server

下面是我在SQL Server中拥有的表,

Title           value
-------------   -------
abc_ef_1_123    53.2
abc_ef_1_1      43.2
abc_ef_1_11     23.1
abc_ef_1_12     45.2
abc_ef_1_13     56.4
def_cef_3_23    98.1
def_cef_3_3     53.2
def_cef_3_12    43.2
def_cef_3_13    23.1
def_cef_3_123   45.2

需要按如下第三个“ _”之前的值对行进行分组,

从表1中按标题分组选择标题,最大值(值)作为值;

结果应该是

title     value
--------- -----
abc_ef_1  56.4
def_cef_3 98.1

请协助。

4 个答案:

答案 0 :(得分:2)

我相信这可以很好地完成工作(用您的表名替换“ Test”):

;with cte as (
  select 
    left(Title, len(Title) - charindex('_', reverse(Title) + '_')) as Title, 
    Value
  from Test
)

select cte.Title, MAX(cte.value)
from cte
group by cte.Title

现在,要精确拍摄第三个下划线, 创建下面文章指示的功能,然后应用以下查询以获得所需的结果。将凌乱的逻辑内联起来有点直观,因此使用这样的函数即可。 http://www.sqlservercentral.com/scripts/Miscellaneous/30497

使用上面链接中的Sql Server函数进行

查询:

;with cte as (
  select 
    LEFT(Title, dbo.CHARINDEX2('_', Title, 3) - 1) as Title, 
    Value
  from Test
)

select cte.Title, MAX(cte.value)
from cte
group by cte.Title

祝你好运!

答案 1 :(得分:1)

with
  sample_data (title, value) as (
    select 'abc_ef_1_123' , 53.2 from dual union all
    select 'abc_ef_1_1'   , 43.2 from dual union all
    select 'abc_ef_1_11'  , 23.1 from dual union all
    select 'abc_ef_1_12'  , 45.2 from dual union all
    select 'abc_ef_1_13'  , 56.4 from dual union all
    select 'def_cef_3_23' , 98.1 from dual union all
    select 'def_cef_3_3'  , 53.2 from dual union all
    select 'def_cef_3_12' , 43.2 from dual union all
    select 'def_cef_3_13' , 23.1 from dual union all
    select 'def_cef_3_123', 45.2 from dual
  )
select   substr(title, 1, instr(title, '_', 1, 3) - 1) as title, max(value) as value
from     sample_data
group by substr(title, 1, instr(title, '_', 1, 3) - 1);

TITLE       VALUE
----------- -----
abc_ef_1     56.4
def_cef_3    98.1

主要收获是,您可以按自己喜欢的任何表达式进行分组,而不仅限于按列分组。另外,您必须在GROUP BYSELECT中重复相同的表达式;遗憾的是,SELECT中给定的别名(名称,标签)不能像GROUP BY中那样使用。 (如果表达式比这种情况复杂得多,则可以先在子查询中创建别名,然后在聚合外部查询中使用别名。)

当然,在这种情况下甚至更糟,因为您想在输出中使用相同的列名title。如果要按title中的GROUP BY进行分组,则将按输入表中的列进行分组,而不是按SELECT中的表达式进行分组。这就是为什么您在输出中执行的操作通常是不好的做法的原因:由于新列与基表中的内容不同,因此请给它一个不同的名称,而不是title。我只是勉强跟随了你的领导。

答案 2 :(得分:0)

您可以使用regexp_substr()

select regexp_substr(title, '[^_]*_[^_]*_[^_]*', 1, 1),
       max(value)
from t
group by regexp_substr(title, '[^_]*_[^_]*_[^_]*', 1, 1);

答案 3 :(得分:0)

  

选择

     

左(标题,charindex(“ [_]”,标题,charindex(“ [_]”,标题,   charindex(’[_]’,标题)))))

     

,Max(Value)

     

来自Tbl

     

分组依据

     

左(标题,charindex(“ [_]”,标题,charindex(“ [_]”,标题,   charindex(’[_]’,标题)))))