Có sự khác biệt giữa việc chuẩn bị một cặp tên-giá trị cho một lệnh và sử dụng env trong bash không?


19

Hãy nói rằng tôi gọi A=B commandenv A=B commandvào bash. Có bất kỳ tình huống nào có thể có một sự khác biệt giữa cả hai điều khoản?

Câu trả lời:


26

Chúng phục vụ cùng một mục đích (truyền các lọ env đã cho cho lệnh). Tuy nhiên, một vài khác biệt đáng chú ý:

A=B command

là một cấu trúc shell (Bourne / POSIX / rc).

Chẳng hạn, bạn có thể làm:

A=B find . -exec cmd '{}' +

hoặc là:

find . -exec env A=B cmd '{}' +

Nhưng bạn không thể làm:

find . -exec A=B cmd '{}' +

Bởi vì findkhông gọi shell để chạy lệnh đó.

Mặt khác, envlà một lệnh bên ngoài, bạn không thể làm:

f() { ...; }
env A=B f

hoặc là:

env A=B eval '...'

Cũng thế:

A=B cmd

chỉ hoạt động với các env vars là tên biến shell hợp lệ . Bạn cần envcho bất kỳ tên var env khác:

env 'my var=foo' cmd...

bashđặt lại _biến:

bash-4.3$ _=xxx env | grep '^_='
_=/usr/bin/env
bash-4.3$ env _=xxx env | grep '^_='
_=xxx

Trong zsh, ARGV0STTYcó ý nghĩa đặc biệt trong bối cảnh đó:

STTY=-echo cat

Chạy catvới thiết bị đầu cuối bị echovô hiệu hóa. Và:

ARGV0=foo cmd

chạy cmdvới foonhư của nó argv[0].

Nếu bạn không muốn xử lý đặc biệt, bạn phải sử dụng env.

Lưu ý rằng sudohỗ trợ:

sudo A=B cmd

Đó không phải là sử dụng vỏ hoặc envđể làm điều đó. Nó tự làm điều đó.

Nó có thể truyền các biến với bất kỳ tên nào ngoại trừ những tên bắt đầu bằng -.

Chuyển nhượng là một cấu trúc shell trong khi một dấu bằng trong đối số envkhông có ý nghĩa đặc biệt với shell, vì vậy A=$B cmdan toàn trong khi env A="$B" cmd(hoặc sudo A="$B" cmd) yêu cầu dấu ngoặc kép.

Các A=B cmdcú pháp chỉ được hỗ trợ trong vỏ của Bourne và rcgia đình (không esmặc dù). Trong vỏ của gia đình cshhoặc fishví dụ, bạn phải dùng đến env.

Khi sử dụng trang web của chúng tôi, bạn xác nhận rằng bạn đã đọc và hiểu Chính sách cookieChính sách bảo mật của chúng tôi.
Licensed under cc by-sa 3.0 with attribution required.