Вывод команды Hive INSERT OVERWRITE DIRECTORY не разделяется разделителем. Зачем?
Файл, который я загружаю, разделяется символом '' (пробел). Ниже находится файл. Файл находится в HDFS: -
001 000
001 000
002 001
003 002
004 003
005 004
006 005
007 006
008 007
099 007
1 > Я создаю внешнюю таблицу и загружаю файл, выдавая следующую команду: -
CREATE EXTERNAL TABLE IF NOT EXISTS graph_edges (src_node_id STRING COMMENT 'Node ID of Source node', dest_node_id STRING COMMENT 'Node ID of Destination node') ROW FORMAT DELIMITED FIELDS TERMINATED BY ' ' STORED AS TEXTFILE LOCATION '/user/hadoop/input';
2 > После этого я просто вставляю таблицу в другой файл, вызывая следующую команду: -
INSERT OVERWRITE DIRECTORY '/user/hadoop/output' SELECT * FROM graph_edges;
3 > Теперь, когда я cat файл, поля не разделяются каким-либо разделителем: -
hadoop dfs -cat /user/hadoop/output/000000_0
Вывод: -
001000
001000
002001
003002
004003
005004
006005
007006
008007
099007
Может кто-нибудь, пожалуйста, помогите мне? Почему удаляется разделитель и как разграничить выходной файл?
В команде CREATE TABLE я попробовал DELIMITED BY '\t'
, но затем я получаю ненужный столбец NULL.
Любые указатели помогают оценить. Я использую версию Hive 0.9.0.
Ответы
Ответ 1
Проблема заключается в том, что HIVE не позволяет вам указать выходной разделитель - https://issues.apache.org/jira/browse/HIVE-634
Решением является создание внешней таблицы для вывода (с указанием спецификации разделителя) и вставка таблицы перезаписи вместо каталога.
-
Предполагая, что у вас есть /user/hadoop/input/graph _edges.csv в HDFS,
hive> create external table graph_edges (src string, dest string)
> row format delimited
> fields terminated by ' '
> lines terminated by '\n'
> stored as textfile location '/user/hadoop/input';
hive> select * from graph_edges;
OK
001 000
001 000
002 001
003 002
004 003
005 004
006 005
007 006
008 007
099 007
hive> create external table graph_out (src string, dest string)
> row format delimited
> fields terminated by ' '
> lines terminated by '\n'
> stored as textfile location '/user/hadoop/output';
hive> insert into table graph_out select * from graph_edges;
hive> select * from graph_out;
OK
001 000
001 000
002 001
003 002
004 003
005 004
006 005
007 006
008 007
099 007
[[email protected]] hadoop fs -get /user/hadoop/output/000000_0 .
Возвращается, как указано выше, с пробелами.
Ответ 2
Я думаю, используя функцию concat_ws, вы можете достичь своего результата;
INSERT OVERWRITE DIRECTORY '/user/hadoop/output' SELECT concat_ws (',', col1, col2) FROM graph_edges;
здесь я выбрал запятую как разделитель столбцов
Ответ 3
В то время как вопрос более 2 лет, и верхний ответ был правильным в то время, теперь можно сказать, что Hive пишет данные с разделителями в каталог.
Вот пример вывода данных с помощью традиционного разделителя ^ A:
INSERT OVERWRITE DIRECTORY '/output/data_delimited'
SELECT *
FROM data_schema.data_table
И теперь с разделителями табуляции:
INSERT OVERWRITE DIRECTORY '/output/data_delimited'
row format delimited
FIELDS TERMINATED BY '\t'
SELECT *
FROM data_schema.data_table
Ответ 4
У меня есть другой голос.
Действительно, Hive не поддерживает пользовательский разделитель.
Но когда вы используете INSERT OVERWRITE DIRECTORY
, в ваших строках есть разделители. Разделитель '\1'
.
Вы можете использовать hadoop dfs -cat $file | head -1 | xxd
, чтобы узнать это или получить файл с HDFS на локальный компьютер и открыть его с помощью vim. Будет некоторый char как '^ A' в вашем vim, который является разделителем.
Вернемся к вопросу. Вы можете использовать простой способ его решения.
-
По-прежнему используйте INSERT OVERWRITE DIRECTORY '/user/hadoop/output'
для генерации /user/hadoop/output
;
-
Создайте внешнюю таблицу, поля которой ограничены '\1'
:
create external table graph_out (src string, dest string)
row format delimited
fields terminated by '\1'
lines terminated by '\n'
stored as textfile location '/user/hadoop/output';
Ответ 5
Вы можете предоставить разделитель при записи в каталоги
INSERT OVERWRITE DIRECTORY '/user/hadoop/output'
ROW FORMAT DELIMITED
FIELDS TERMINATED BY
SELECT * FROM graph_edges;
Это должно сработать для вас.
Ответ 6
По умолчанию разделитель "^ A" . В языке python это "\ x01" .
Когда я хочу изменить разделитель, я использую SQL как:
SELECT col1, разделитель, col2, разделитель, col3,...,
FROM table
Затем рассмотрите разделитель + "^ A" как новый разделитель.
Ответ 7
Я подозреваю, что куст на самом деле пишет contol-A в качестве деминера, но когда вы делаете кошку на экране, это не отображается вам на глаза.
Вместо этого попробуйте открыть файл в vi или загладить файл, если вы хотите увидеть его немного, и vi результат:
hadoop dfs -cat/user/hadoop/output/000000_0 | head > my_local_file.txt
vi my_local_file.txt
Вы должны уметь видеть символы ^ A.
Ответ 8
У меня была эта проблема, когда вывод результатов запроса куста должен быть ограничен линией.
Запуск этой команды sed можно заменить: ^A to |
sed 's#\x01#|#g' test.log > piped_test.log
Ответ 9
Это было бы лучшим решением, я полагаю, хотя его круг вокруг пути достижения.
INSERT OVERWRITE DIRECTORY '/user/hadoop/output' SELECT src_node_id, '', dest_node_id FROM graph_edges;
Ответ 10
вы можете использовать этот параметр "поля с разделителями строк, прерванные символом '|'" , например, в вашем случае должно быть
INSERT OVERWRITE DIRECTORY '/user/hadoop/output' поля с разделителями строк с разделителями строк, прерванные '|' SELECT * FROM graph_edges;