我有以下csv文件的内容
以下是CSV文件的内容:
Date_Added|this_flag|Name|DOB|SSN|ID
2015年5月1日| Y | Jingle | heimerscmidt | 19901002 | 123456789 | 3
May 1st, 2015|N|Jingleheimerscmidt|19901002|123456789|3
May 5th, 2015|Y|Jon|19901001|012345678|1
May 1st, 2015|N|Jon|19901002|012345678|1
May 1st, 2015|Y|Jacob|19901001|234567890|2
May 5th, 2015|N|Jingleheimerscmidt|19901001|123456789|3
May 1st, 2015|Y|Jingleheimerscmidt|19901001|123456789|3
正如您在粗体和斜体内容中所看到的,除了管道操作符separted columns之外,内容中还有一个管道操作符。我想从文本中删除该管道操作符而不打开csv文件。有没有办法通过编写代码或任何其他方法来解决这个问题
答案 0 :(得分:0)
好吧,我知道你标记了oracle,所以也许你自己或其他Oracle专家可以从sql-server迁移这个解决方案。我知道oracle能够完成这些操作。
通常我会说你想要快速/奇特的方式来分割字符串,但在这种情况下你需要在分隔符之间保持字符串的顺序位置。所以我想到了一种可以做到这一点的方法。
1)首先将CSV作为全1列导入临时表。现在,如果你的CRLF也在Name列中找到,那么这将是一个问题....但我们认为它不是因为你没有指定它。
2)在该表上构建一个row_number以用作假主键,并确定何时有更多的分隔符。
3)使用递归cte将字符串溢出到行中,并在原始字符串中维护子字符串的序号位置,以便以后连接。
4)通过MergePositions改变OrdinalPostion并基于它生成DENSE_RANK()来确定要分组的行
5)条件聚合使用OrdinalGroup作为列号,然后使用连接方法组合所有OrdginalGroup 3行。
DECLARE @CSV as TABLE (LumpedColumns NVARCHAR(MAX))
INSERT INTO @CSV VALUES
('May 1st, 2015|Y|Jingle|he|imerscmidt|19901002|123456789|3')
,('May 1st, 2015|N|Jingleheimerscmidt|19901002|123456789|3')
,('May 5th, 2015|Y|Jon|19901001|012345678|1')
,('May 1st, 2015|N|Jon|19901002|012345678|1')
,('May 1st, 2015|Y|Jacob|19901001|234567890|2')
,('May 5th, 2015|N|Jingleheimerscmidt|19901001|123456789|3')
,('May 1st, 2015|Y|Jingleheimerscmidt|19901001|123456789|3')
;WITH cteFakePrimaryKey AS (
SELECT
LumpedColumns
,CASE WHEN LEN(LumpedColumns) - LEN(REPLACE(LumpedColumns,'|','')) > 5 THEN
LEN(LumpedColumns) - LEN(REPLACE(LumpedColumns,'|','')) - 5 ELSE 0 END as MergeXPositions
,ROW_NUMBER() OVER (ORDER BY (SELECT 0)) as PK
FROM
@CSV
)
, cteRecursive AS (
SELECT
PK
,LumpedColumns
,MergeXPositions
,LEFT(LumpedColumns,CHARINDEX('|',LumpedColumns)-1) as ColValue
,RIGHT(LumpedColumns,LEN(LumpedColumns) - CHARINDEX('|',LumpedColumns)) as Remaining
,1 As OrdinalPosition
FROM
cteFakePrimaryKey
UNION ALL
SELECT
PK
,LumpedColumns
,MergeXPositions
,LEFT(Remaining,CHARINDEX('|',Remaining)-1)
,RIGHT(Remaining,LEN(Remaining) - CHARINDEX('|',Remaining))
,OrdinalPosition + 1
FROM
cteRecursive
WHERE
Remaining IS NOT NULL AND CHARINDEX('|',Remaining) > 0
UNION ALL
SELECT
PK
,LumpedColumns
,MergeXPositions
,Remaining
,NULL
,OrdinalPosition + 1
FROM
cteRecursive
WHERE Remaining IS NOT NULL AND CHARINDEX('|',Remaining) = 0
)
, cteOrdinalGroup AS (
SELECT
PK
,LumpedColumns
,ColValue
,OrdinalPosition
,DENSE_RANK() OVER (PARTITION BY PK ORDER BY
CASE
WHEN OrdinalPosition < 3 THEN OrdinalPosition
WHEN OrdinalPosition > (3 + MergeXPositions) THEN OrdinalPosition
ELSE 3 END ) as OrdinalGRoup
FROM
cteRecursive
)
SELECT
PK
,LumpedColumns
,MAX(CASE WHEN OrdinalGRoup = 1 THEN ColValue END) as Date_Added
,MAX(CASE WHEN OrdinalGRoup = 2 THEN ColValue END) as this_flag
,STUFF(
(SELECT '|' + ColValue
FROM
cteOrdinalGroup g2
WHERE
g1.PK = g2.PK
AND g2.OrdinalGroup = 3
ORDER BY
g2.OrdinalPosition
FOR XML PATH(''))
,1,1,'') as name
,MAX(CASE WHEN OrdinalGRoup = 4 THEN ColValue END) as DOB
,MAX(CASE WHEN OrdinalGRoup = 5 THEN ColValue END) as SSN
,MAX(CASE WHEN OrdinalGRoup = 6 THEN ColValue END) as ID
FROM
cteOrdinalGroup g1
GROUP BY
PK
,LumpedColumns
ORDER BY
PK
答案 1 :(得分:0)
如果这只是您需要处理的一个案例而您不想修改文件而您需要在Informatica中执行此操作,则可以更改此Input Type
的{{1}}会话属性Source Qualifier
到File
并使用sed进行替换,例如:
Command
这不是一个非常好的解决方案,因此它不是一般的解决方案。但也许这会或者至少会给你一些想法。