2016-06-30 3 views
2

я пример файл с именем «test.in», как показано ниже, с передними и задними пространствами:Удаление пробелов из всех элементов массива

Hi | hello how | are you? 
I need | to remove | leading & trailing 
spaces | where ever | it's located 

мне нужно поставить элементы, разделенные «|» в массиве с «\ n» в качестве основного разделителя.

Я хочу, чтобы каждый элемент массива не имел передних или конечных пробелов, допускались только пробелы между символами. Я использую образец кода для проверки результатов, прежде чем я ставил код, это мое основное развертывание.

Часть образца сценария:

OIFS="$IFS" 
IFS=$'\n' 
while read LINE 
do 
IFS='|' 
my_tmpary=($LINE) 
echo ${my_tmpary[@]} 
my_ary=`echo ${my_tmpary[@]} | awk '$1=$1'` 
echo ${my_ary[@]} 
done < test.in 

Я хотел бы не использовать цикл, чтобы очистить лишние пробелы. Я пробовал & методы ошибок с помощью sed, awk, tr, но пока это не для меня.

my_ary [@] должно быть, как это

Hi hello how are you? 
I need to remove leading & trailing 
spaces where ever it's located 
+2

Ваш вопрос не очень ясен в данный момент .. Вы хотите обрезать пробелы вокруг '' '.В любом случае всегда полезно поставить образец вывода, чтобы выразить себя лучше. – sjsam

+0

Также 'my_ary' не является массивом. Он просто содержит результат результата команды 'echo $ {my_tmpary [@]} | awk '$ 1 = $ 1'', который является строкой. – sjsam

+0

Остановитесь, вы подходите совершенно неправильно, и вы даже не должны иметь массив оболочек. См. [Why-is-use-a-shell-loop-to-process-text -emed-bad-practice] (http://unix.stackexchange.com/questions/169716/why-is-using-a-shell -loop-процесс-текст рассмотренной-плохая практика). Если вы публикуете новый вопрос с кратким тестируемым вводом проб и ожидаемым результатом, мы можем помочь вам сделать это правильно. –

ответ

2
sed -E 's/[\t]{1,}/ /g;s/^ *| *$//g;s/[ ]{2,}/ /g;s/ *\| */ /g;' test.in 

должны это сделать. Таким образом:

$ my_ary=$(sed -E 's/[\t]{1,}/ /g;s/^ *| *$//g;s/[ ]{2,}/ /g;s/ *\| */ /g;' test.in) 
$ echo "$my_ary" 
Hi hello how are you? 
I need to remove leading & trailing 
spaces where ever it's located 
This lines has many tabs 

решает вашу проблему.


Примечание 1. s/[\t]{1,}/ /g преобразует вкладки, т.е. \t в непечатаемые. 2. s/^ *| *$//g удаляет ведущие пробелы &. 3. s/[ ]{2,}/ /g сжимает несколько пробелов. 4. s/ *\| */|/g удаляет пробелы около | 5. -E позволяет использовать расширенное регулярное выражение с sed.

+0

Я думаю, вы правы в том, что OP также хочет удалить пробелы до и после '|'. – andlrc

+0

@andlrc: Ну, я думаю, это то, что op хотел сделать здесь, да! :) – sjsam

+0

Переход к первому символу 's/^ * \ | * $ // g' также обрабатывать конечные пробелы. – choroba

3

Вы можете (аб) использовать тот факт, что чтение будет удалять начальные и конечные пробелы при IFS по умолчанию:

while read -r line; do 
    printf "%s\n" "$line" # Leading and trailing spaces are removed. 
done < test.in 

Альтернатива Вы можете СЭД для такой задачи:

sed 's/^[[:space:]]*\|[[:space:]]*$//g' test.in 
+0

printf был приятным прикосновением – sjsam

+0

, что sed не будет работать, вы соответствуете полной строке, а затем используете g по какой-то причине. – 123

+0

@ 123 Там есть чередование ('\ |'). – andlrc

1

В AWK:

awk '{gsub(/^ *| *$|/,"",$0); gsub(/ *\| *| +/," ",$0); print $0}' test.in 

gsub(/^ *| *$|/,"",$0) удалить начальное и конечное пространство , gsub(/ *\| *| +/," ",$0) заменить космические космические комбо и несколько пробелов с одним пространством, print $0 распечатать всю запись. $ 0 может быть пропущен, как @mona_sax прокомментировал, но для ясности я оставил его в коде.

Конечно, это может быть петельные и каждый разделителями поля трубы обрезается отдельно:

awk -F\| -v OFS=" " '  # set input field separator to "|" and output separator to " " 
function trim(str) { 
    gsub(/^ *| *$/,"",str); # remove leading and trailing space from the field 
    gsub(/ +/," ",str);  # mind those multiple spaces as well 
    return str    # return cleaned field 
} 
{ 
    for(i=1;i<=NF;i++)  # loop thru all pipe separated fields 
    printf "%s%s", trim($i),(i<NF?OFS:ORS) # print field and OFS or 
}           # output record separator in the end of record 
' test.in 

.

+1

'print $ 0' является избыточным. 'print' по умолчанию означает' print $ 0'. Также удалите вкладки на вкладке. –

+1

@mona_sax, и вы также можете сказать 'awk '{gsub (...)} 1' файл'. Это '1' (или любое другое значение True) имеет значение True и запускает' {print $ 0} '. – fedorqui

+0

@fedorqui: Конечно, вы можете! : D Это еще более идиоматический и элегантный способ сделать это. –

Смежные вопросы