2015-10-12 7 views
0

Ok. Заголовок может быть запутанным, но для разработки у меня есть файл в unix, который уже является разделителем с табуляцией, и я пытаюсь использовать bcp в этом. Но проблема заключается в одном столбце, где некоторые случайные значения имеют вкладку внутри него. Но на самом деле это не случайным образом. Вкладка в этом столбце содержит только значения двойной кавычки. Эта дополнительная вкладка может быть сразу после двойной цитаты или непосредственно перед и между словами внутри двойных кавычек.Найдите и замените вкладку на пробелы для определенного шаблона в файле unix, который разделен на вкладку как разделитель полей

Поэтому я хочу заменить эти вкладки на космос.

Для например

HAPPINESS  ALEXIS JORDAN "HAPPINESS  "  CASH 024  Producer    ABRAMUS QUARTERLY  HAPPINESS  D658 Columbia  D658 Columbia  C283 Columbia Records Group 1Q15 
HAPPINESS  ALEXIS JORDAN "HAPPINESS  ALWAYS" CASH 024  Producer    ABRAMUS QUARTERLY  HAPPINESS  D658 Columbia  D658 Columbia  C283 Columbia Records Group 1Q15 
HAPPINESS  DEADMAU5/ALEXIS JORDAN "  HAPPINESS  "  CASH 024  Producer    ABRAMUS QUARTERLY  HAPPINESS  D658 Columbia  D658 Columbia  C283 Columbia Records Group 1Q15 

Вы можете найти вышеуказанный текст для справки. Пожалуйста, помогите. Заранее спасибо.

+0

Забыл добавить вкладку в каждой строке внутри двойных кавычек. –

ответ

0

Вы можете использовать этот gnu-awk commandto преобразовать вкладки внутри кавычек: вход

awk -v FPAT='"[^"]+"|[^\t]+' '{for (i=1; i<=NF; i++) if ($i ~ /^"/) 
     gsub(/\t/, " ", $i)} 1' OFS='\t' file 

FPAT='"[^"]+"|[^\t]+' перерыва на поля либо в двойных кавычках, или если они разделены табуляцией.

Выход с cat-vt из данного образца:

awk -v FPAT='"[^"]+"|[^\t]+' '{for (i=1; i<=NF; i++) if ($i ~ /^"/) gsub(/\t/, " ", $i)} 1' OFS='\t' file|cat -vt 
HAPPINESS^IALEXIS^IJORDAN^I"HAPPINESS "^ICASH^I024^IProducer^IABRAMUS^IQUARTERLY^IHAPPINESS^ID658^IColumbia^ID658^IColumbia^IC283^IColumbia^IRecords^IGroup^I1Q15 
HAPPINESS^IALEXIS^IJORDAN^I"HAPPINESS ALWAYS"^ICASH^I024^IProducer^IABRAMUS^IQUARTERLY^IHAPPINESS^ID658^IColumbia^ID658^IColumbia^IC283^IColumbia^IRecords^IGroup^I1Q15 
HAPPINESS^IDEADMAU5/ALEXIS^IJORDAN^I" HAPPINESS "^ICASH^I024^IProducer^IABRAMUS^IQUARTERLY^IHAPPINESS^ID658^IColumbia^ID658^IColumbia^IC283^IColumbia^IRecords^IGroup^I1Q15 
+0

Спасибо за ответ. Но вышеприведенная команда заменит вкладку до первой двойной кавычки и после второй двойной цитаты. Я не хочу этого. Я хочу заменить любую вкладку в двух двойных квотах, и просто добавить файл уже с разделителем табуляции. TIA. Ayush –

+0

Не уверен, что вы подразумеваете под этим, как выводя результат в моем ответе, вы можете видеть эту вкладку перед первой двойной цитатой, то есть '' HAPPINESS' не был заменен. – anubhava

0

Рассмотрим с помощью Perl:

perl -pe 's{"\K(.*?)(?=")}{$1 =~ tr/\t/ /r}eg' filename 

Это заменяет все соответствует по регулярному выражению "\K(.*?)(?=") с результатом выражения $1 =~ tr/\t/ /r. Модификаторы eg необходимы для замены g (если в строке имеется более одной строки, указанной в строке) и с заменой вычисленных ошибок e.

Things отметить:

  • Все, прежде чем \K должен быть там что-то, чтобы быть матч, но делает это на самом деле не часть матча.
  • (?=") - это термин, который рассматривается; это соответствует пустой строке, если она сопровождается "
  • .*? соответствует любой строке, не жадность, т.е. берется кратчайший фитинг матч, а не самое длинный

Таким образом, регулярное выражение соответствует всем между " и следующим " и фиксирует его как $1. Выражение в заменяющей статье возвращает значение этого захвата с заменой вкладок пробелами, и оно выполняется в тех местах, где раньше использовалась исходная строка.

+0

Я пробовал с приведенным выше кодом, и я получил это. perl -pe '{"\ K (. *?) (? =")} {$ 1 = ~ tr/\ t// r} например' объединенный_ppb_20151001.txt21 Базис найден там, где оператор ожидал на -e строке 1 , рядом с "tr/\ t// r" синтаксическая ошибка при -e строке 1, около "tr/\ t// r" Выполнение -e прерывается из-за ошибок компиляции. У меня нет большой идеи по perl .. Пожалуйста, помогите. TIA –

+0

Я немного поработал и обнаружил, что мой perl имеет более старую версию. поэтому я удалил/r, но теперь получаю «Модификация значения, доступного только для чтения, на -e строке 1, <> строка 1». Пожалуйста, помогите. –

+0

Модификатор 'r' в' tr', 's' и т. Д. Существует с Perl 5.14. Если ваш Perl старше, используйте 'perl -pe 's {" \ K (. *?) (? = ")} {$ X = $ 1; $ x = ~ tr/\ t//; $ x}, например 'filename'. Создание копии необходимо, потому что '$ 1' является значением только для чтения и' = ~ tr/\ t// 'без' r' пытается изменить левую сторону. – Wintermute