입력을 전달할 때 어떤 방법이 더 좋나요?
> echo 'test' | base64
dGVzdAo=
> base64 <<< 'test'
dGVzdAo=
또한 변수의 경우 어떤 방법을 사용해야 합니까?
> t='test'
> echo "$t" | base64
dGVzdAo=
> base64 <<< "$t"
dGVzdAo=
답변1
<<<
zsh
here-string은 1990년대 초반에 도입된 here-document(및 Unix 포트)의 약식 형식 rc
이며 이후 많은 다른 셸에 (변형과 함께) 복사되었습니다.
여기에 설명된 것과 동일한 방식으로 구현됩니다. 및 을 포함한 zsh
대부분의 셸에서는 bash
Bourne 셸(1970년대 후반에 여기에 문서를 도입한 셸)에서 수행되는 것처럼 임시 파일을 삭제하여 이를 수행합니다.
이 작업을 수행할 때:
cmd <<< 'something'
쉘은 비슷한 작업을 수행합니다.
file=$(mktemp)
printf 'something\n' > "$file"
{
rm -f -- "$file" && cmd
} < "$file"
(물론 이러한 명령을 실행하지 않고 모든 mktemp
, printf
, rm
은 내부적으로 수행됩니다.)
일부 셸은 파이프와 별도의 프로세스(분기된 명령 또는 작은 파일/문자열이 될 수 있는 기본 셸 프로세스)를 사용하여 데이터를 제공합니다. 일부 쉘은 /dev/null
빈 here 문서를 사용하도록 되돌아갈 수 있습니다(여기 문자열은 rc
개행 문자가 추가되지 않는 한 비어 있을 수 없습니다).
임시 파일을 사용하여 구현하면 몇 가지 장점이 있습니다.
- 분기된 프로세스가 없습니다.
- 입력은 검색 가능합니다. 명령은 입력에서 데이터를 앞뒤로 읽고 다른 위치에서 다시 읽을 수 있지만 입력이 파이프인 경우에는 이를 수행할 수 없습니다. 그러나 이식 가능한
sh
스크립트 에서는 이에 의존할 수 없습니다 .
몇 가지 단점:
- 콘텐츠는 다음을 제외하고
zsh
NUL 바이트를 포함할 수 없습니다 . - 이외의
rc
개행 문자로 끝나지 않는 입력은 제공할 수 없습니다. - 임시 파일 생성이 실패할 수 있습니다(예: 남은 공간이 없거나 일부 구현이 너무 제한적인 경우)
$TMPDIR
.umask
- 데이터는 영구 저장소에 저장됩니다. 파일이 삭제되기 전에 삭제되더라도
read
데이터는 결국 디스크에 커밋될 수 있습니다. 즉, 누군가 디스크를 얻을 수 있으면 복구할 수 있습니다.
존재하다:
printf '%s\n' "$something" | cmd
(여기서 as printf
대신 사용하는 것은 임의의 데이터와 함께 사용할 수 없습니다).echo
echo
동시에 실행되는 두 개의 프로세스가 있는데, 하나는 파이프를 통해 다른 하나에 출력을 제공합니다. AT&T를 cmd
사용하는 내장 명령이나 복합 명령 또는 함수인 경우 해당 명령 은 현재 셸에서 실행되지만 그렇지 않으면 하위 프로세스에서 실행되므로 이와 유사한 작업이 작동하지 않습니다.zsh
ksh
bash -o lastpipe
echo x | read var
이렇게 하면 다음과 같은 이점이 있습니다.
- 이식 가능하다( 의 반대
<<<
,<<
이식 가능하다) <<<
위에서 언급한 단점은 없음zsh
쉘 (zsh
내장 명령에 NUL 바이트를 전달할 수 있는 유일한 쉘) 이외의 쉘에서 NUL 바이트를 제공하려면 다음을 수행할 수 있습니다printf '\0' | cmd
.
결점:
cmd
위에서 언급한 것처럼 추가 프로세스와 일부 쉘의 하위 프로세스에서 실행된다는 사실- 입력 내용을 검색할 수 없습니다.
base64 인코딩을 원하는 경우 test
다음과 같습니다.
printf test | base64
또는
printf %s "$data" | base64
임의의 데이터의 경우.
Base64 인코딩이 제공됩니다 test<newline>
.