bash 스타일 배열을 ash로 포팅하는 방법은 무엇입니까?

bash 스타일 배열을 ash로 포팅하는 방법은 무엇입니까?

나는 얼마 전에 bash 스크립트를 작성했는데 이제는 ash.

이는 다음 bash과 같습니다:

services=( "service1.service"
           "service2.service"                                       
           "service3.service" )  

for service in "${services[@]}"
do
   START $service                   
done

START()
{
   echo "Starting "$1
   systemctl start $1
}

현실적으로 배열에는 약 40개의 서비스가 있으며 이러한 전환을 최대한 쉽고 깔끔하게 만들고 싶습니다. 항상 bash교리를 사용합니다. 이제 나는 스크립트의 이식성을 높이는 작업에 직면했습니다.

이식성의 이유로 순수한 ash솔루션을 사용하는 것이 더 좋습니다. 하지만 제가 사용할 수 있는 매우 강력한 장치가 있기 때문에 busybox휴대성을 어느 정도 희생할 수도 있습니다. 가독성이 크게 향상되는 경우에만 "깨끗한" 스크립트도 지표가 됩니다.

그것은 무엇입니까?가지고 다닐 수 있는그리고깨끗한이 경우 해결책은?

답변1

배열이 및 기타 쉘에 나타나기 전에 일반적인 접근 방식은 어떤 요소에도 없는 구분 기호(또는 bash필요한 ksh이스케이프를 최소화하기 위한 흔하지 않은 구분 기호)를 선택하고 이 구분 기호로 구분된 모든 A 문자열 요소를 반복하는 것입니다. 공백은 일반적으로 쉘이 기본적으로 "단어"를 공백으로 분할하기 때문에 가장 편리한 구분 기호 선택입니다(다른 내용으로 분할하려면 IFS를 설정할 수 있음).

예를 들어:

# backslash-escape any non-delimiter whitespace and all other characters that
# have special meaning to the shell, e.g. globs, parenthesis, ampersands, etc.
services='service1.service service2.service service3.service'

for s in $services ; do  # NOTE: do not double-quote $services here.
  START "$s"
done

$services~해야 한다아니요여기서는 큰따옴표로 묶었습니다. 왜냐하면 우리는생각하다쉘은 그것을 "단어"로 나눕니다.

답변2

ash에는 배열이 없습니다. 가까이 다가가는 유일한 것은 위치 매개변수이므로 다음과 같은 작업을 수행할 수 있습니다.

set -- "service1.service" \
       "service2.service" \
       "service3.service"

for service in "$@"
do
   START $service
done

답변3

서비스 목록을 한 번만 참조해야 하는 경우 여기에서 설명서를 사용할 수 있습니다.

while IFS= read -r service
do
   START "$service"
done << END
service1.service
service2.service
service3.service
END

서비스 이름은 목록에 인용되어서는 안 됩니다( "$service"타당한 이유가 없는 한 인용되어야 하지만). 서비스 이름을 들여쓰려면 <<-not을 사용 <<하고 탭을 사용하여 이름을 들여쓰십시오.

while IFS= read -r service
do
   START "$service"
done <<- END
        service1.service
        service2.service
        service3.service
END

답변4

fix 접두사가 붙은 변수를 생성하여 배열을 시뮬레이션할 수 있습니다.

예시 1:

#!/bin/ash

# simulate array variables
comment_wifi='wifi-text'
comment_status='some-state'
comment_0=1234
comment_1=7878
comment_2=9999

for v in wifi status $(seq 0 2)
do
 # construct variable and get its value
 eval value="\$comment_${v}"

 echo "comment_${v}: ${value}"
done

산출:

comment_wifi: wifi-text
comment_status: some-state
comment_0: 1234
comment_1: 7878
comment_2: 9999

예 2:

#!/bin/ash

# fill create and variables 
for v in wifi status $(seq 0 2)
do
  # example value
  a_value="$(cat /proc/uptime)"

  # construct variable and assign value
  eval comment_${v}="\$a_value";
done

# output
for v in wifi status $(seq 0 2)
do
 # construct variable and get its value
 eval value="\$comment_${v}";

 echo "comment_${v}: ${value}"
done

산출:

comment_wifi: 5954.23 22504.11
comment_status: 5954.24 22504.12
comment_0: 5954.24 22504.14
comment_1: 5954.25 22504.16
comment_2: 5954.25 22504.17

관련 정보