listagg 数据转换为可用格式?

Posted

技术标签:

【中文标题】listagg 数据转换为可用格式?【英文标题】:listagg data to useable format? 【发布时间】:2015-05-02 23:04:37 【问题描述】:

这是我第一次使用 LISTAGG 函数,我很困惑。我可以很容易地选择数据,但是USERS 列的字符之间都有空格,并且在尝试复制粘贴时,不会复制该列中的数据。我尝试过两种不同的 IDE。我是不是做错了什么?

例子:

select course_id, listagg(firstname, ', ') within group (order by course_id) as users
    from (
      select distinct u.firstname, u.lastname, u.student_id, cm.course_id
      from course_users cu
      join users u on u.pk1 = cu.users_pk1
      join course_main cm on cm.pk1 = cu.crsmain_pk1
      and cm.course_id like '2015SP%'
      )
group by course_id;

产量:

【问题讨论】:

你能告诉我们“格式奇怪”是什么意思吗?您没有得到的预期输出是什么? @ruudvan 为清楚起见进行了编辑。 USERS 列的字符之间都有空格,当尝试复制粘贴时,不会复制该列中的数据。 子查询返回用户名不带空格? 无法复制可能是由于 IDE 中的某些问题。您使用的是哪个 IDE? (如 Toad 或 plsql 开发人员)?此外,查询中似乎没有任何添加空格的内容。独立运行子查询以确保表中的数据中没有这些空格。 @ruudvan 我已经尝试过 dbForge Studio Express 和 Oracle SQL Developer。两者的行为相同。 【参考方案1】:

显然这是 11 中的一个已知(未解决?)错误。TO_CHAR() 为我工作...

SELECT wiporderno, LISTAGG(TO_CHAR(medium), ',') WITHIN GROUP(ORDER BY wiporderno) AS jobclassification 

...medium 是有问题的列/数据类型。

【讨论】:

IMO 值得添加 bug# 和简短描述:Bug 19461687 LISTAGG return value contains ASCII 0x00 bytes for NVARCHAR with no delimiter specified (MOS Doc ID: 19461687.8)【参考方案2】:

您的firstname 列似乎定义为nvarchar2

with t as (
  select '2015SP.BOS.PPB.556.A'as course_id,
    cast('Alissa' as nvarchar2(10)) as firstname
  from dual
  union all select '2015SP.BOS.PPB.556.A'as course_id,
    cast('Dorothea' as nvarchar2(10)) as firstname
  from dual
)
select course_id, listagg(firstname, ', ')
  within group (order by course_id) as users
from t
group by course_id;

COURSE_ID            USERS                         
-------------------- ------------------------------
2015SP.BOS.PPB.556.A 

...我也无法从 SQL Developer 复制/粘贴用户值,但它显示为空格,正如您从 SQL*Plus 中看到的那样:

COURSE_ID            USERS
-------------------- ------------------------------
2015SP.BOS.PPB.556.A  A l i s s a,  D o r o t h e a

如文档所述,listagg() 函数始终返回 varchar2(或 raw),因此传入 nvarchar2 值会导致隐式转换,从而丢弃您的结果。

如果您的列属于该数据类型,您可以在 listagg 调用中将其转换为 varchar2

column users format a30
with t as (
  select '2015SP.BOS.PPB.556.A'as course_id,
    cast('Alissa' as nvarchar2(10)) as firstname
  from dual
  union all select '2015SP.BOS.PPB.556.A'as course_id,
    cast('Dorothea' as nvarchar2(10)) as firstname
  from dual
)
select course_id, listagg(cast(firstname as varchar2(10)), ', ')
  within group (order by course_id) as users
from t
group by course_id;

COURSE_ID            USERS                         
-------------------- ------------------------------
2015SP.BOS.PPB.556.A Alissa, Dorothea               

但你可能根本不希望它是nvarchar2

【讨论】:

【参考方案3】:

我有类似的问题,原来是编码的问题。我像这样解决了这个问题(如果需要,更改为另一种编码):

...listagg(convert(firstname, 'UTF8', 'AL16UTF16'), ', ')...

【讨论】:

Oracle discourages the use of convert 虽然,如文档中所述;即使这是为了更正存储在错误字符集中的数据。如果varchar2nvarchar2 存储之间存在差异,那么强制转换似乎更合适。如果您有更广泛的字符集问题,那么这可能不安全。取决于,就像很多事情一样...... @AlexPoole 为什么会这样?这篇文章似乎表明这是应该使用它的时间。 @Cliff - 只是指出警告。如果这两个字符集是您的数据库和国家字符集,那么它会起作用,但我会先看看为什么您的字符集错误。

以上是关于listagg 数据转换为可用格式?的主要内容,如果未能解决你的问题,请参考以下文章

MAPGIS的WL\WP\WT数据可否成批转换成ARCGIS数据格式?转换后是不是可用

查询将过去 11 个会计年度作为行返回。我可以使用 LISTAGG() 将其转换为逗号分隔的列表吗?

listagg 列转换

求解:怎么将r软件内的数据转换为excel数据?

尽管列为可用格式,但将 ogg 转换为 wav 不起作用

将 HTML 代码转换为纯文本,格式可用于文本文件 [重复]