Shell script: nếu nhiều điều kiện


7

Tôi muốn tạo một tập lệnh shell lặp lại một cái gì đó nếu 3 thư mục không tồn tại.

Đây là đoạn mã tôi đã viết: test.sh:

if [ ! -d "/home/unix/POSTagger2" ] || [! -d "/home/unix/POSTagger2/stanford-parser-full-2015-12-09"] || [! -d "/home/unix/POSTagger2/stanford-corenlp-full-2015-12-09"]; then
echo "Nope"
fi

Khi tôi chạy nó, tôi gặp lỗi này:

./test.sh: line 1: [!: command not found

Có gì sai với cú pháp của tôi?


Trong điều kiện đầu tiên, bạn đã có nó đúng. Làm tương tự trong điều kiện thứ hai sẽ là điều đầu tiên tôi thực hiện được
glglgl

[không phải là mã thông báo, nó là một lệnh (tên gọi khác của lệnh test) vì vậy nó phải được phân tách bằng dấu cách. Trường hợp tương tự là ]tham số lệnh nên nó cũng phải được phân tách bằng khoảng trắng.
pabouk

Câu trả lời:


15

Bạn đang thiếu một số khoảng trắng, ví dụ [!phải [ !"]phải " ]xem mã đã sửa:

#!/bin/bash
if 
[ ! -d "/home/unix/POSTagger2" ] || 
[ ! -d "/home/unix/POSTagger2/stanford-parser-full-2015-12-09" ] || 
[ ! -d "/home/unix/POSTagger2/stanford-corenlp-full-2015-12-09" ] 
then
      echo "Nope"
fi

Một cách khác cho mã của bạn:

#!/bin/bash
for dir in "/home/unix/POSTagger2" "/home/unix/POSTagger2/stanford-parser-full-2015-12-09" "/home/unix/POSTagger2/stanford-corenlp-full-2015-12-09"; do
     if [ ! -d "$dir" ]; then echo nope ; break; fi 
done  

9

Bạn cần một khoảng trống giữa [!để mọi thứ hoạt động chính xác. Điều này là do [được triển khai dưới dạng lệnh shell-buildin (thậm chí nó từng được sử dụng như một ngoại lệ riêng biệt /usr/bin/[).

Bạn cũng có thể dùng:

if [ ! -d "/home/unix/POSTagger2" -o ! -d "/home/unix/POSTagger2/stanford-parser-full-2015-12-09" -o ! -d "/home/unix/POSTagger2/stanford-corenlp-full-2015-12-09") ] ; then
    echo "Nope"
fi

Bash cung cấp một sự thay thế [[được thực hiện như biểu thức en. [[sử dụng &&, ||vv thay vì -a, -onhư các nhà khai thác.

if [[ ! (-d "/home/unix/POSTagger2" && -d "/home/unix/POSTagger2/stanford-parser-full-2015-12-09" && -d "/home/unix/POSTagger2/stanford-corenlp-full-2015-12-09") ]] ; then
    echo yes
fi

Chỉnh sửa: Cảm ơn các bình luận từ @LucianoAndressMartini và @pabouk vì những sửa đổi quan trọng theo sự hiểu biết của tôi.


1
Không! Bạn sai rồi. Hãy thử chuyển / usr / bin / [sang thư mục khác và bạn thấy rằng câu lệnh có điều kiện vẫn hoạt động tốt vì nó được tích hợp sẵn, tệp thực thi này bạn thấy không được sử dụng bởi bash, nó được cung cấp dưới dạng tùy chọn tương thích đối với một số shell cổ, vì vậy chúng có thể chạy một số mã bash mà không gặp lỗi.
Luciano Andress Martini

3
Đó là một lệnh dựng sẵn trong bash, nhưng thực tế là nó hoạt động như bất kỳ lệnh nào và cần một khoảng trắng vẫn được áp dụng.
ilkkachu

1
Có phần này của câu trả lời vẫn được áp dụng. Đó là một câu trả lời tuyệt vời, điều sai lầm duy nhất là về suy nghĩ rằng "[" không phải là một vỏ được tích hợp sẵn.
Luciano Andress Martini

1
Vâng, tôi đã học được một cái gì đó mới! Tôi không bao giờ sửa đổi quan điểm của tôi [kể từ năm 1999, rõ ràng.
Satya Mishra

1
[[không phải là một lệnh. Nó là một mã thông báo và một số ký tự đặc biệt có ý nghĩa khác nhau giữa [[]]. Ngoài ra, nó không tuân thủ POSIX và chỉ hoạt động trong một số shell như bash hoặc korn. Xem ví dụ mywiki.wooledge.org/BashFAQ/031
pabouk
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.