LINUX.ORG.RU

цикл в bash

 


0

1

Добрый день! Столкнулись со следующей проблемой: Есть файл «ip» с содержанием -

10.10.10.1=of
10.20.20.1=sh
#10.10.30.1=of
10.30.50.2=sh

Задача: Посмотреть этот файл до конца, выдать результат для of - то что стоит перед «=», и sh то-же самое.

Например:

10.10.10.1=of
в строке есть of, значит пишем 10.10.10.1 в ip_ip

10.20.20.1=sh
в строке есть sh, значит пишем 10.20.20.1 в ip_sh

В циклах я не силен, смог только выбрать вторую часть после =, которые не закомментированы:

for ip in `cat ip | grep -v '^#' | cut -d"=" -f2`; do echo $ip; done

далее ступор.
Как сюда встроить

if [[ $ip == 'of' ]] then ... else ...
, а самое главное как дойти до конца файла и все это дело не зациклить

Прошу помощи.



Последнее исправление: letti (всего исправлений: 1)

#!/bin/bash

IPS="127.0.0.1=of 128.0.0.1=sh"

for ip in $IPS; do
 echo ${ip#*=} : ${ip%%=*}
done
Deleted
()
$ cat test.txt 
10.10.10.1=of
10.20.20.1=sh
#10.10.30.1=of
10.30.50.2=sh
$ grep '^[^#]' test.txt | while read i ; do IFS='=' ; j=($i) ; unset IFS ; [[ "${j[1]}" = "sh" ]] && echo "${j[0]}" ; done
10.20.20.1
10.30.50.2
$ 
sin_a ★★★★★
()
Ответ на: комментарий от sin_a

Этот вариант мне подошел. Спасибо!

letti
() автор топика

awk -vFS== '!/^#/ && $2 == «of» {print $1}'

anonymous
()
grep -Po '^[^#]+(?==of)' ip.txt
anonymous
()

sed -n '/#/! s/=of//p'

anonymous
()
Ответ на: комментарий от sin_a

Но IFS лучше сохранять и восстанавливать. А уж первый символ сравнивать вызовом внешней программы (grep) при наличии bash совсем тяп-ляпно. Вот даже без bash-измов, работает для конфига в том числе с комментариями по '#' после строки с адресом и флагом (оно само так получилось) :) :

#!/bin/ash

# cat cfg.txt
10.10.10.1=of
10.20.20.1=sh #special
#10.10.30.1=of
10.30.50.2=sh

#cat parser.sh
parser_ip_str() {
        local l ip flg
        while read l; do
                l=${l%#*}
                [ -z "$l" ] && continue
                ip=${l%=*}
                flg=${l#*=}
                if [ of = "$flg" ]; then
                        ip_ip="$ip_ip${ip_ip:+ }$ip"
                elif [ sh = "$flg" ]; then
                        ip_sh="$ip_sh${ip_sh:+ }$ip"
                fi
        done < "$1"
}

parser_ip_str cfg.txt
echo "ip_ip=$ip_ip ip_sh=$ip_sh"

vodz ★★★★★
()
Последнее исправление: vodz (всего исправлений: 1)
Ответ на: комментарий от sin_a

unset IFS восстанавливает до ожидаемого состояния.

Можно придерживаться устоявшейся терминологии? Ожидаемого... Мдэ.

Ну и чтобы два раза не вставать, конструкция j=($i) небезопасна без set -f

vodz ★★★★★
()
Ответ на: комментарий от vodz

Ну ты хочешь его сохранить и восстановить? Значит ожидаешь от него какого то состояния. Когда я использовал этот приём то пробовал задавать пробел, ещё что-то, оказалось unset в данном случае спасает всех. А какая здесь терминология устоялась, я не знаю.

И, да, мне переопределять как массив тоже не нравится. Но сочетание смены IFS и read -a здесь у меня что-то не вышло.

А что ты здесь делаешь с переменными — вообще вне моего понимания. Хотя для сложных случаев, наверно действительно всё таки лучше брать другие инструменты.

sin_a ★★★★★
()
Ответ на: комментарий от anonymous

read без -r использовать небезопасно.

Вот тут как раз наоборот, конфиги могут содержать продолжение строк по \

vodz ★★★★★
()
Ответ на: комментарий от anonymous

А \ в ip благополучно «проглотится»

И это правильно.

У ТСа не конфиг, у него файл с записями ip=(of|sh).

Это и есть конфиг.

vodz ★★★★★
()
Ответ на: комментарий от vodz

И это правильно.

При обработке при помощи awk/grep/sed этот \ неожиданно всплывет.

Это и есть конфиг.

А я думал, это данные в самопальном формате, которому line continuation как собаке пятая нога.

anonymous
()
Ответ на: комментарий от anonymous

А я думал, это данные в самопальном формате, которому line continuation как собаке пятая нога.

Ну подумайте, почему -r не по умолчанию. Правильно, то что есть данные для скрипта shell-а, есть для shell-а, а не для awk и \<CR> удобное дополнение.

vodz ★★★★★
()
Ответ на: комментарий от vodz

Ну подумайте, почему -r не по умолчанию.

Так сложилось исторически.

anonymous
()
Вы не можете добавлять комментарии в эту тему. Тема перемещена в архив.