Hive 插入查询,如 SQL

Posted

技术标签:

【中文标题】Hive 插入查询,如 SQL【英文标题】:Hive insert query like SQL 【发布时间】:2013-06-29 19:33:37 【问题描述】:

我是 Hive 新手,想知道是否有像我们在 SQL 中那样将数据插入 Hive 表的方法。我想将我的数据插入蜂巢中

INSERT INTO tablename VALUES (value1,value2..)

我了解到您可以将数据从文件加载到 hive 表,或者您可以将数据从一个表导入到 hive 表,但是有没有办法像在 SQL 中一样附加数据?

【问题讨论】:

hive post 0.14 版本支持 ACID 属性。所以可以插入,更新删除是可能的,但对于单行和单条件操作。cwiki.apache.org/confluence/display/Hive/… 【参考方案1】:

向Hive表中插入数据的方式: 为了演示,我使用表名作为 table1table2

    create table table2 as select * from table1 where 1=1; 要么 create table table2 as select * from table1;

    insert overwrite table table2 select * from table1; --它将数据从一个插入另一个。注意:它会刷新目标。

    insert into table table2 select * from table1; --它将数据从一个插入另一个。注意:它将附加到目标中。

    load data local inpath 'local_path' overwrite into table table1; --它将数据从本地加载到目标表中并刷新目标表。

    load data inpath 'hdfs_path' overwrite into table table1; --它将从hdfs位置加载数据并刷新目标表。 或

    创建表table2( col1 字符串, col2 字符串, col3 字符串) 以“,”结尾的行格式分隔字段 位置'hdfs_location';

    load data local inpath 'local_path' into table table1; --它将从本地加载数据并附加到目标表中。

    load data inpath 'hdfs_path' into table table1; --它将从hdfs位置加载数据并附加到目标表中。

    insert into table2 values('aa','bb','cc'); --假设table2只有3列。

    多次插入hive表

【讨论】:

【参考方案2】:

是的,我们可以在 Hive 中使用插入查询。

hive> create table test (id int, name string);

INSERT:INSERT...VALUES 从 0.14 版开始可用。

hive> insert into table test values (1,'mytest');

这适用于insert。我们必须使用values 关键字。

注意:用户不能使用INSERT INTO...VALUES 子句将数据插入到复杂数据类型列(数组、映射、结构、联合)中。

【讨论】:

【参考方案3】:

设置几个属性以使 Hive 表支持 ACID 属性并将值插入到表中,就像在 SQL 中一样。

在 Hive 中创建 ACID 表的条件。

    该表应存储为 ORC 文件。目前只有 ORC 格式可以支持 ACID 属性。 表必须分桶

用于创建 ACID 表的属性:

set hive.support.concurrency =true;
set hive.enforce.bucketing =true;
set hive.exec.dynamic.partition.mode =nonstrict
set hive.compactor.initiator.on = true;
set hive.compactor.worker.threads= 1;
set hive.txn.manager = org.apache.hadoop.hive.ql.lockmgr.DbTxnManager;

在 hive.site.xml 中将属性 hive.in.test 设置为 true

设置所有这些属性后,应使用 tblproperty 'transactional' ='true' 创建表。该表应分桶并保存为 orc

CREATE TABLE table_name (col1 int,col2 string, col3 int) CLUSTERED BY col1 INTO 4 

BUCKETS STORED AS orc tblproperties('transactional' ='true');

现在可以像 SQL 查询一样将值插入到表中。

INSERT INTO TABLE table_name VALUES (1,'a',100),(2,'b',200),(3,'c',300);

【讨论】:

【参考方案4】:

您可以使用表格生成函数stack 将文字值插入表格中。

首先,您需要一个只包含一行的虚拟表。你可以在limit的帮助下生成它。

CREATE TABLE one AS
SELECT 1 AS one
FROM any_table_in_your_database
LIMIT 1;

现在您可以使用如下文字值创建一个新表:

CREATE TABLE my_table AS
SELECT stack(3
  , "row1", 1
  , "row2", 2
  , "row3", 3
) AS (column1, column2)
FROM one
;

stack 的第一个参数是您正在生成的行数。

您还可以向现有表添加值:

INSERT INTO TABLE my_table
SELECT stack(2
  , "row4", 1
  , "row5", 2
) AS (column1, column2)
FROM one
;

【讨论】:

【参考方案5】:

您也可以为特定的列添加值,只需指定要在其中添加相应值的列名:

Insert into Table (Col1, Col2, Col4,col5,Col7) Values ('Va11','Va2','Val4','Val5','Val7');

确保您跳过的列没有空值类型。

【讨论】:

【参考方案6】:

您仍然可以在 Hive 中插入复杂类型 - 它可以工作 (id 为 int,同事数组)

insert into emp(id,colleagues) select 11, array('Alex','Jian') from (select '1')

【讨论】:

【参考方案7】:

输入以下命令,在某些条件下将数据插入到 testlog 表中:

INSERT INTO TABLE testlog SELECT * FROM table1 WHERE some condition;

【讨论】:

【参考方案8】:

table2 的全部数据插入table1。下面是一个查询:

INSERT INTO TABLE table1 SELECT * FROM table2; 

【讨论】:

【参考方案9】:

这里的一些答案在 Hive 0.14 中已经过时了

https://cwiki.apache.org/confluence/display/Hive/LanguageManual+DML#LanguageManualDML-InsertingvaluesintotablesfromSQL

现在可以使用如下语法插入:

CREATE TABLE students (name VARCHAR(64), age INT, gpa DECIMAL(3, 2));

INSERT INTO TABLE students
  VALUES ('fred flintstone', 35, 1.28), ('barney rubble', 32, 2.32);

【讨论】:

【参考方案10】:

unique2 建议的稍微好一点的版本如下:

insert overwrite table target_table
select * from 
(
select stack(
    3,                 # generating new table with 3 records
    'John', 80,        # record_1
    'Bill', 61         # record_2
    'Martha', 101      # record_3
    ) 
) s;

这不需要使用已经存在的表进行破解。

【讨论】:

为什么要在select栈外加select语句,有必要吗?【参考方案11】:

您可以使用以下方法。有了这个,您不需要创建临时表或 txt/csv 文件来分别进一步选择和加载。

INSERT INTO TABLE tablename SELECT value1,value2 FROM tempTable_with_atleast_one_records LIMIT 1.

其中 tempTable_with_atleast_one_records 是具有至少一条记录的任何表。

但这种方法的问题在于,如果您有插入多行的 INSERT 语句,如下面的行。

INSERT INTO yourTable values (1 , 'value1') , (2 , 'value2') , (3 , 'value3') ;

然后,您需要为每一行设置单独的 INSERT hive 语句。见下文。

INSERT INTO TABLE yourTable SELECT 1 , 'value1' FROM tempTable_with_atleast_one_records LIMIT 1;
INSERT INTO TABLE yourTable SELECT 2 , 'value2' FROM tempTable_with_atleast_one_records LIMIT 1;
INSERT INTO TABLE yourTable SELECT 3 , 'value3' FROM tempTable_with_atleast_one_records LIMIT 1;

【讨论】:

【参考方案12】:

是的,您可以插入,但不像 SQL。

在SQL中我们可以插入行级数据,但是这里可以按字段(列)插入。

在此期间,您必须确保目标表和查询应具有相同的数据类型和相同的列数。

例如:

CREATE TABLE test(stu_name STRING,stu_id INT,stu_marks INT)
ROW FORMAT DELIMITED
FIELDS TERMINATED BY ','
STORED AS TEXTFILE;

INSERT OVERWRITE TABLE test SELECT lang_name, lang_id, lang_legacy_id FROM export_table;

【讨论】:

【参考方案13】:

您绝对可以将数据附加到现有表中。 (但它实际上不是 HDFS 级别的附加)。只是每当您在没有OVERWRITE 子句的情况下对现有 Hive 表执行 LOAD 或 INSERT 操作时,都会放入新数据而不替换旧数据。将为该表对应的目录中新插入的数据创建一个新文件。例如:

我有一个名为 demo.txt 的文件,它有 2 行:

ABC
XYZ

创建一个表并将这个文件加载到其中

hive> create table demo(foo string);
hive> load data inpath '/demo.txt' into table demo;

现在,如果我在这张桌子上执行 SELECT,它会给我:

hive> select * from demo;                        
OK    
ABC    
XYZ

假设,我还有一个名为 demo2.txt 的文件:

PQR

我在这个表上再次执行 LOAD 而不使用覆盖,

hive> load data inpath '/demo2.txt' into table demo;

现在,如果我现在执行 SELECT,它会给我,

hive> select * from demo;                       
OK
ABC
XYZ
PQR

HTH

【讨论】:

【参考方案14】:

我认为在这种情况下,您应该使用 HBASE,它有助于这种插入,但它不提供任何 SQL 类型的查询语言。您需要像 put 方法一样使用 HBASE 的 Java API 来进行这种插入。此外,HBASE 是面向列的 no-sql 数据库。

【讨论】:

【参考方案15】:

您不能插入到插入单条记录。 Hive 不支持它。您可以将要插入的所有新记录放入文件中,然后将该文件加载到 Hive 中的临时表中。然后使用 insert overwrite..select 命令将这些行插入到主 Hive 表的新分区中。这里的约束是您的主表必须预先分区。如果您不使用分区,那么您的整个表将被这些新记录替换。

【讨论】:

不完全正确。 “INSERT INTO 将追加到表或分区,保持现有数据完好无损。(注意:INSERT INTO 语法仅从 0.8 版本开始可用)”cwiki.apache.org/confluence/display/Hive/…【参考方案16】:

没有。 Hive 目前不支持这种INSERT INTO tablename VALUES (x,y,z) 语法。

【讨论】:

有没有办法让我可以像在 SQL 中那样在表中追加数据。 支持INSERT INTO tablename SELECT ...,因此您可以将新数据放在临时表中,然后从中选择插入。 我想通过 java 客户端在 hive 中追加数据,如果我在 java 中创建一个临时数据表并仅在我的 java 客户端中编写插入和选择查询,它会工作吗? 如果你使用Java,为什么不直接追加到HDFS中的文件呢? Hive 不太适合这种东西。

以上是关于Hive 插入查询,如 SQL的主要内容,如果未能解决你的问题,请参考以下文章

在 HIVE 上插入 Spark-SQL 插件

Pyodbc 未检测 SQL 语句中的参数标记(即 - 插入表 SELECT ...)到 Hive 表。这个问题有解决方法吗?

用python连接hive和presto并进行查询和插入

如果列数不同,如何处理从源 spark df 到 hive 表的插入

hql语句怎么写向Hive中一次插入一条数据或一个字段的值,类似关系型数据库的sql语句?

无法查询/选择通过Spark SQL插入的数据