我有一个如下所示的文件:
33.49.147.163 20140416123526 https://news.google.com/topstories?hl=en-US&gl=US&ceid=US:en 29 409 Firefox/5.0
我想将其加载到配置单元表中。我这样做:
create external table Logs (
ip string,
ts timestamp,
request string,
page_size smallint,
status_code smallint,
info string
)
row format serde 'org.apache.hadoop.hive.serde2.RegexSerDe'
with serdeproperties (
"timestamp.formats" = "yyyyMMddHHmmss",
"input.regex" = '^(\\S*)\\t{3}(\\d{14})\\t(\\S*)\\t(\\S*)\\t(\\S*)\\t(\\S*).*$'
)
stored as textfile
location '/data/user_logs/user_logs_M';
还有
select * from Logs limit 10;
结果
33.49.147.16 NULL https://news.google.com/topstories?hl=en-US&gl=US&ceid=US:en 29 409 Firefox/5.0
如何正确解析时间戳,以避免出现 NULL?
最佳答案
“timestamp.formats”
SerDe 属性 works only with LazySimpleSerDe (存储为文本文件
),它不适用于RegexSerDe
。如果您使用 RegexSerDe,则解析查询中的时间戳。
在 CREATE TABLE 中将 ts
列定义为 STRING
数据类型,并在查询中将其转换如下:
select timestamp(regexp_replace(ts,'(\\d{4})(\\d{2})(\\d{2})(\\d{2})(\\d{2})(\\d{2})','$1-$2-$3 $4:$5:$6.0')) as ts
当然,您可以使用 SerDe 作为单独的列提取时间戳的每个部分,并在查询中将它们与分隔符正确连接以获得正确的时间戳格式,但这不会给您带来任何改进,因为无论如何您都需要额外的转换查询。
关于regex - 创建表期间解析 Hive 中的时间戳,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/70313933/