内容纲要
问题描述
关于quote.delim,官方解释是:
'quote.delim'
属性的值指定用什么字符作为 quote_delimiter
,默认值为“"”
。这个字符的作用为:如果字段本身包含了字段分隔符、换行符或者NULL
值字符作为数据的一部分,将该字段放在两个 quote_delimiter
字符之间可以让Inceptor将字段内部出现的字段分隔符和换行符作为数据处理。同时,在一对 quote_delimiter
包裹的字段内部,quote_delimiter
是自身的转义符:如果出现连续的两个 quote_delimiter
,那么Inceptor会将第二个 quote_delimiter
作为数据的一部分处理,将第一个 quote_delimiter
作为第二个的转义符。
quote.delim
为双引号的情况下,要求双引号内的双引号必须偶数对出现,如果连续出现,代表着对双引号的转义,而单个单个的出现,双引号会带到数据里面去,是有意义的。
如果非偶数对出现,就会出现数据行数丢失的情况,全部堆在一列里面。
详细说明
下面构造一个简单的场景复现问题:
构建样例表:
DROP TABLE TRANSACTIONS;
CREATE external TABLE TRANSACTIONS(
trans_id int DEFAULT NULL ,
acc_num string DEFAULT NULL ,
trans_time string DEFAULT NULL,
trans_type string DEFAULT NULL,
stock_id string DEFAULT NULL,
price double DEFAULT NULL,
amount int DEFAULT NULL)
STORED AS CSVFILE
LOCATION '/tmp/lkw115'
TBLPROPERTIES(
'field.delim'=',',
'quote.delim'='"',
'line.delim'='\n') ;
1、正常情况:quote_delimiter为双引号时,里面的双引号偶数个出现
--第二列,双引号内的双引号偶数对出现,所以正常展示
"943197522","651"a"3065","20140105100520","b","AA7105670","12.13","200"
"943197523","652"b"3066","20140105100521","c","AA7105671","12.14","201"
2、异常情况1:quote_delimiter为双引号时,里面的双引号奇数个出现,后面不再出现这样的字符组合
由于该字符串包裹内,以及后面的字符串,找不到结尾的那个双引号,所以该字段囊括了后面的所有数据(甚至包括了line.delim的换行符),后面字段的数据全部为null。最终的表现就是,2行数据,实际上只有1行数据load到了csv外表
--下面这行,"651"a”3065",字母a后面是中文双引号。
--所以最终结果是,实际2行数据,导致最终csvfile表的查询结果为1行。
"943197522","651"a”3065","20140105100520","b","AA7105670","12.13","200"
"943197523","652"b"3066","20140105100521","c","AA7105671","12.14","201"
3、异常情况2:quote_delimiter为双引号时,里面的双引号奇数个出现,后面再次出现这样的字符组合
由于在该字符串包裹内找不到结尾的那个双引号,所以该字段囊括了后面的所有数据(甚至包括了line.delim的换行符),直到在第三行同样的异常数据列,找到了另外一个双引号,所以最终的表现就是,3行数据,实际上只有1行数据load到了csv外表
--第一行,"651"a”3065",字母a后面是中文双引号
--第三行,"653"c”3067",字母c后面是中文双引号
--所以最终结果是,实际3行数据,导致最终csvfile表的查询结果为1行。
"943197522","651"a”3065","20140105100520","b","AA7105670","12.13","200"
"943197523","652"b"3066","20140105100521","c","AA7105671","12.14","201"
"943197524","653"c”3067","20140105100522","d","AA7105672","12.15","202"