Lưu ý: Để biết giải pháp tương thích với POSIX, hãy xem câu trả lời này .
${BASH_SOURCE[0]}
(hoặc đơn giản hơn, $BASH_SOURCE
[1]
) chứa đường dẫn (có khả năng tương đối) của tập lệnh chứa trong tất cả các trường hợp gọi, đặc biệt là khi tập lệnh được lấy nguồn , điều này không đúng với $0
.
Hơn nữa, như Charles Duffy đã chỉ ra, người gọi $0
có thể đặt thành một giá trị tùy ý .
Mặt khác, $BASH_SOURCE
có thể để trống, nếu không có tệp được đặt tên nào liên quan; ví dụ:
echo 'echo "[$BASH_SOURCE]"' | bash
Ví dụ sau đây minh họa điều này:
Tập lệnh foo
:
#!/bin/bash
echo "[$0] vs. [${BASH_SOURCE[0]}]"
$ bash ./foo
[./foo] vs. [./foo]
$ ./foo
[./foo] vs. [./foo]
$ . ./foo
[bash] vs. [./foo]
$0
là một phần của đặc tả trình bao POSIX, trong khi BASH_SOURCE
, như tên cho thấy, là dành riêng cho Bash.
[1] Đọc tùy chọn: ${BASH_SOURCE[0]}
vs.$BASH_SOURCE
:
Bash cho phép bạn tham chiếu phần tử 0
của một biến mảng bằng cách sử dụng ký hiệu vô hướng : thay vì viết ${arr[0]}
, bạn có thể viết$arr
; nói cách khác: nếu bạn tham chiếu biến như thể nó là một đại lượng vô hướng , bạn sẽ nhận được phần tử ở chỉ mục 0
.
Sử dụng tính năng này che khuất thực tế rằng $arr
là một mảng, đó là lý do tại sao mã shell phổ biến linter shellcheck.net đưa ra cảnh báo sau (tính đến thời điểm viết bài này):
SC2128: Mở rộng mảng không có chỉ mục chỉ đưa ra phần tử đầu tiên.
Một lưu ý nhỏ: Mặc dù cảnh báo này hữu ích, nhưng nó có thể chính xác hơn, vì bạn sẽ không nhất thiết phải nhận được phần tử đầu tiên : Đó là phần tử cụ thể tại chỉ mục 0
được trả về, vì vậy nếu phần tử đầu tiên có chỉ số cao hơn - thì là có thể trong Bash - bạn sẽ nhận được chuỗi trống; thử 'a[1]='hi'; echo "$a"'
.
(Ngược lại,zsh
, bao giờ những phản bội, thực sự không trả về phần tử đầu tiên, bất kể chỉ mục của nó).
Bạn có thể chọn để tránh tính năng này do tính không rõ ràng của nó, nhưng nó hoạt động có thể đoán trước được và nói một cách thực dụng, bạn sẽ hiếm khi cần truy cập vào các chỉ số khác ngoài 0
biến mảng ${BASH_SOURCE[@]}
.
BASH_SOURCE
đã được thêm vào lúc bash-3.0-alpha. Bạn có thể không có, tùy thuộc vào chế độ kiểm tra của bạn. Tôi thấy nó bị thiếu trên cả Solaris và OS X. Ngoài ra, hãy xem return: chỉ có thể trả về từ một hàm hoặc tập lệnh có nguồn gốc trên U & L.SE.