
네 줄로 구성된 텍스트 파일이 있는데 각 줄에는 1, 2, 3, 4가 있습니다. 또한 병렬화하려는 함수가 있습니다.foo() { echo "$1 is not $2"; }
함수를 내보냅니다.export -f foo
이제 병렬화를 위해 텍스트 파일의 매개변수를 사용하여 함수를 호출하고 싶습니다 xargs
.그리고a=0
또한 변수()를 함수의 매개변수로 사용하고 싶습니다 . 그래서 저는 함수를 호출했습니다.cat txt | xargs -I "{}" -P 2 bash -c 'foo {} $a'
하지만이는 변수( a=0
)를 무시합니다. 그리고 출력:
"1은 아님"..."4는 아님" 등
호출하면 cat txt | xargs -I "{}" -P 2 bash -c 'foo {} 0'
작동하고 올바른 출력을 얻습니다.
"1은 아니야0"..." 4 아니오0"등
a=0
하지만 0을 사용하는 대신 변수()를 사용하여 호출 해야 합니다 . 어떻게 해야 합니까?
답변1
쉘 코드에 포함시키는 것은 {}
명령 주입 취약점을 야기하므로 항상 나쁜 생각입니다. 데이터를 별도의(코드가 아닌) 매개변수로 전달하는 것이 항상 더 좋습니다.
또한 / -I
가 없으면 따옴표와 백슬래시를 차단하고 선행 공백을 제거합니다. GNU (이미 GNU 확장을 사용하고 있기 때문에 사용해야 함 )의 경우 각 입력 줄을 별도의 인수로 전달하는 것이 좋습니다-d
-0
xargs
-P
-d '\n'
xargs -a txt -rd'\n' -P2 -n1 bash -c 'foo "$2" "$1"' bash "$a"
( 인라인 쉘 스크립트에서는 sum이라고 하는 별도의 인수로 현재 행의 내용을 사용하여 각 입력 행 bash
에 대해 한 번씩 호출이 수행됩니다.)1
$a
$1
$2
또는 다음을 사용하여 -I
:
xargs -a txt -rd'\n' -P2 -I'{}' bash -c 'foo "$1" "$2"' bash {} "$a"
여기에서 별도의 쉘 호출을 실행하거나 함수를 내보낼 필요가 없는 기능을 포함하여 GNU처럼 병렬화 할 수 zsh
있는 zargs
자동 로드 가능한 기능 으로 전환할 수 있습니다 .xargs
xargs
$ autoload zargs
$ foo() print -r - $1 is not $2
$ zargs -P2 -I {} {1..4} -- foo {} $a
1 is not foo
2 is not foo
3 is not foo
4 is not foo
답변2
GNU Parallel을 사용하면 다음과 같습니다:
foo() { echo "$1 is not $2"; }
export -f foo
seq 4 > txt
a=0
cat txt | parallel foo {} $a