Đúng,
nl='
'
case $var in
(*"$nl"*) echo yes;;
(*) echo no;;
esac
(theo nguyên tắc, tôi muốn trích dẫn tất cả các mở rộng biến trong case
mẫu trừ khi tôi muốn chúng được coi là mẫu, mặc dù ở đây nó không tạo ra sự khác biệt vì $nl
không chứa ký tự đại diện).
hoặc là
case $var in
(*'
'*) echo yes;;
(*) echo no;;
esac
Tất cả nên hoạt động và tuân thủ POSIX, và những gì tôi sẽ sử dụng cho điều đó. Nếu bạn loại bỏ (
s, nó thậm chí sẽ hoạt động trong vỏ Bourne cũ.
Đối với một cách khác để đặt $nl
biến:
eval "$(printf 'nl="\n"')"
Lưu ý rằng $'\n'
được lên kế hoạch đưa vào phiên bản tiếp theo của tiêu chuẩn POSIX . Nó đã được hỗ trợ bởi ksh93
, zsh
, bash
, mksh
, busybox và FreeBSD sh
ít nhất (tính đến tháng 2 năm 2018).
Về việc thử nghiệm bạn có là đủ hay không, bạn đã có một thử nghiệm cho cả hai trường hợp, vì vậy sẽ thử nghiệm tất cả các đường dẫn mã.
Hiện tại có một thứ không được chỉ định rõ ràng trong thông số POSIX: liệu có *
khớp với chuỗi có chứa chuỗi byte không tạo thành các ký tự hợp lệ hay liệu các biến shell có thể chứa các chuỗi đó hay không.
Trong thực tế, ngoài yash
các biến chỉ có thể chứa các ký tự và ngoài các byte NUL (không có shell nhưng zsh
có thể lưu trữ trong các biến của chúng), *$nl*
phải khớp với bất kỳ chuỗi nào chứa $nl
ngay cả khi chúng chứa các chuỗi byte không hợp lệ các ký tự (như $'\x80'
trong UTF-8).
find
Ví dụ, một số triển khai sẽ không khớp với -name "*$nl*"
chúng, vì vậy nếu thử nghiệm một vỏ mới và nếu bạn có ý định xử lý những thứ không được đảm bảo là văn bản (như tên tệp), bạn có thể muốn thêm trường hợp thử nghiệm cho nó. Thích với:
test=$(printf '\200\n\200')
trong một miền địa phương UTF-8.