EOF và lỗi cú pháp không mong đợi


9

Tôi hiện đang viết kịch bản shell thứ ba của mình và tôi đã gặp phải một vấn đề. Đây là kịch bản của tôi cho đến nay:

#!/bin/bash
echo "choose one of the following options : \
  1) display all current users \
  2) list all files \
  3) show calendar \
  4) exit script"

while read  
do  
 case in  
        1) who;;  
        2) ls -a;;  
        3) cal;;  
        4) exit;;  
 esac    
done

Khi tôi cố chạy tập lệnh, nó sẽ báo:

line2 : unexpected EOF while looking for matching '"'  
line14 : syntax error: unexpected end of file.    

Tôi đang làm gì sai?


1
Chắc chắn bạn có nghĩa là "EOF", không phải "ECF"?
l0b0

Câu trả lời:


5

Vấn đề là, casecâu lệnh của bạn thiếu chủ đề - biến cần đánh giá. Do đó bạn có thể muốn một cái gì đó như thế này:

#!/bin/bash
cat <<EOD
choose one of the following options:
1) display all current users
2) list all files
3) show calendar
4) exit script
EOD

while true; do
    printf "your choice: "
    read
    case $REPLY in
        1) who;;
        2) ls -a;;
        3) cal;;
        4) exit;;
    esac    
done

Ở đây casesử dụng biến mặc định $REPLYreadlấp đầy khi nó không đưa ra bất kỳ tên biến (xem help readđể biết chi tiết).

Cũng lưu ý các thay đổi: printfđược sử dụng để hiển thị lời nhắc trong mỗi vòng (và không nối thêm một dòng mới), catđược sử dụng để in hướng dẫn trên một số dòng để chúng không bao bọc và dễ đọc hơn.


6

Chúng ta đừng quên select:

choices=( 
    "display all current users" 
    "list all files" 
    "show calendar" 
    "exit script"
)
PS3="your choice: "
select choice in "${choices[@]}"; do
    case $choice in
        "${choices[0]}") who;;
        "${choices[1]}") ls -a;;
        "${choices[2]}") cal;;
        "${choices[3]}") break;;
    esac
done

1
Đây có vẻ là câu trả lời sạch nhất cho đến nay. Nó sử dụng select được thiết kế để thực hiện chính xác những gì OP yêu cầu. Nó đặt các lựa chọn trong một mảng là một cách tuyệt vời để xử lý dữ liệu như thế này và làm cho nó có sẵn để sử dụng ở nơi khác trong tập lệnh. Nó sử dụng break thay vì exit để script có thể làm một cái gì đó khác sau khi phần này được thực hiện.
Joe

2

Hãy để chúng tôi cố gắng cho một trường hợp duy nhất ban đầu. Tôi sẽ sử dụng read -pđể đọc đầu vào của người dùng vào một biến opttheo sau là câu lệnh tình huống như dưới đây.

#!/bin/bash
read -p "choose one of the following options : \
  1) display all current users \
  2) list all files \
  3) show calendar \
  4) exit script" opt
case $opt in
1) who;;
2) ls -a;;
3) cal;;
4) exit;;
esac

Kịch bản trên hoạt động tốt và bây giờ, tôi tin rằng bạn cần phải có nó trong một vòng lặp để bạn có thể đọc dữ liệu nhập của người dùng cho đến khi người dùng nhấn tùy chọn 4.

Vì vậy, chúng ta có thể làm điều đó với một whilevòng lặp như dưới đây. Tôi đặt biến optvới giá trị ban đầu là 0. Bây giờ, tôi đang lặp trong whilevòng lặp miễn là optbiến có giá trị là 0 (đó là lý do tại sao tôi đặt lại optbiến là 0 ở cuối casecâu lệnh).

#!/bin/bash
opt=0;
while [ "$opt" == 0 ]
do
read -p "choose one of the following options : \
  1) display all current users \
  2) list all files \
  3) show calendar \
  4) exit script" opt

case $opt in
1) who;;
2) ls -a;;
3) cal;;
4) exit;;
esac
opt=0
done

0

Cá nhân tôi sẽ đặt "while" ở đầu mã. Nếu sau đó bạn làm theo nó với một :, nó sẽ cho phép nó lặp đi lặp lại nhiều lần như bạn muốn. Đây là cách tôi sẽ viết nó.

while :
do
    echo "choose one of the following options : \
      1) display all current users \
      2) list all files \
      3) show calendar \
      4) exit script"
    read string
    case $string in
        1)
            who
            ;;

sau đó tiếp tục các câu hỏi và kết thúc bằng

esac
done
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.