2016-02-13 64 views
1

我有一个像下面的CSV数据:防止LOAD DATA INFILE

"E12 98003";1085894;"HELLA";"8GS007949261";"";1 
"5 3/4"";652493;"HELLA";"9HD140976001";"";1 

一些字段包括在双引号。问题是, ,你可能在第二行看到第一列中的数据包含一个双引号在年底为数据的一部分。

我试图沿着线的东西:

LOAD DATA INFILE file.csv 
INTO TABLE mytable 
FIELDS TERMINATED BY ';' ENCLOSED BY '"' 
LINES TERMINATED BY '\r\n' 

,但它会使用引号的数据逃离现场封闭引号。我也试过ESCAPED BY ''ESCAPED BY '\\'没有成功。 有没有办法阻止LOAD DATA INFILE命令转义双引号? 或者我应该解析csv并且在只有一个时加双引号? 无论如何,我使用powershell解析文件,将编码更改为utf8。有什么方法可以很快解决这个问题吗?我的powershell代码:

function Convert-FileToUTF8 { 

    param([string]$infile, 
      [string]$outfile, 
      [System.Int32]$encodingCode) 

    $encoding = [System.Text.Encoding]::GetEncoding($encodingCode) 
    $text = [System.IO.File]::ReadAllText($infile, $encoding) 
    [System.IO.File]::WriteAllText($outfile, $text) 

} 

好吧,我做了它使用.NET正则表达式来修复csv。这是昂贵的,但不是太多。 我写

$text = [regex]::Replace($text, "(?m)(?<!^)(?<!\;)""(?!\;)(?!\r?$)", '""'); 

只是在函数的最后一行之前,它似乎工作确定。由于我是正则表达式的新手,这可能可以改进。

+1

主要的问题是输入数据是无效的CSV格式,因为属于数据的双引号应该加倍(转义)。所以问题就变成了:你从哪里得到这个无效的CSV,你能做些什么来解决它? – trincot

+0

它是从第三方软件中导出的。不幸的是,我无法控制csv是如何创建的。 – pankal

回答

1

的主要问题是该输入数据构成无效CSV语法,如在RFC-4180所述,第7段:

如果双引号用于括字段,然后一个双引号出现一个字段内必须通过在另一个双引号之前进行转义才能逃脱。

但在你的PowerShell脚本,你可以尝试解决这个问题有一个额外的行,使用replace method$文字,一旦你得到了它的价值:

$text = $text.Replace('"";', '""";') 

这应该是足够的,

如果该字段开头:因为如果他们在其他地方出现在数据上mysql.com(我的高亮显示)作为规定的装载机将转义双引号处理好ENCLOSED BY字符,该字符的实例被识别为终止字段值只有后接字段或行TERMINATED BY序列。

当然,如果格式不正确的CSV数据包含";,那么您仍然有问题。但它是非常难以确定mysql.com因为发现这样的出现是否终止数据或应被视为数据的一部分,甚至对人类:-)

另一件事要注意:

如果输入值未必包含在引号内,请在ENCLOSED BY关键字前使用OPTIONALLY

+0

恐怕您的解决方案将只关注数据末尾的非双引号。 – pankal

+1

是的,但MySql Load会将内部引号视为它们(即使未转义),但前提是它们没有后跟字段或行分隔符。 – trincot

+0

它看起来很好......但是,困扰我的是,这种情况不能得到保证... – pankal