ตรวจสอบความยาวของตัวแปร


27

ฉันจะตรวจสอบความยาวของตัวแปรที่อ่าน (สคริปต์ของฉันใส่ตัวอักษรได้ไม่เกินห้าตัว) ฉันคิดถึงสิ่งนี้:

#!/bin/bash
read string
check=${#string}
echo $check
if [ $check -ge 5 ]; then echo "error" ; exit
else echo "done"
fi

จะมีทางออกที่ "สง่างาม" มากขึ้น?


1
สคริปต์ของคุณทำงานได้อย่างถูกต้องใน /bin/shPOSIX คุณควรพิจารณาเปลี่ยนสาย shebang #!/bin/shเป็นแบบพกพามากขึ้นและทำงานในสภาพแวดล้อมที่ไม่มีการทุบตี นอกจากนี้/bin/shอาจเป็นเปลือกที่เบากว่าเช่นเส้นประซึ่งไม่ได้รับภาระกับคุณสมบัติที่มีไว้สำหรับการใช้งานแบบโต้ตอบ
Celada

@Celada แม้ว่าจริงในกรณีนี้dash's ${#string}จะให้คุณมีความยาวในจำนวนไบต์แทนของตัวละคร
Stéphane Chazelas

คำตอบ:


43

สง่างามมากขึ้น? ไม่

ลงเรื่อย ๆ ? ใช่แล้ว

#!/bin/bash
read string
if [ ${#string} -ge 5 ]; then echo "error" ; exit
else echo "done"
fi

และหากคุณไม่มีปัญหาในการซื้อขายความสง่างามที่มากขึ้นในแง่ที่สั้นลงคุณสามารถมีสคริปต์ที่มี 2 บรรทัดน้อยกว่า:

#!/bin/bash
read string
[ ${#string} -ge 5 ] && echo "error" || echo "done"

คุณสามารถใช้วงเล็บสองชั้นหากคุณคิดว่าปลอดภัยกว่า คำอธิบายที่นี่


3

ทางเลือกที่เข้ากันได้กับบอร์น ( ${#string}เป็น POSIX แต่ไม่ใช่บอร์น (ไม่ใช่ว่าคุณน่าจะเคยเจอเชลล์เชลล์ในสมัยนี้)):

case $string in
  ?????*) echo >&2 Too long; exit 1;;
       *) echo OK
esac

โปรดทราบว่าสำหรับทั้งสอง${#string}และ????ไม่ว่าจะเป็นจำนวนไบต์หรือตัวละครจะขึ้นอยู่กับเปลือก โดยทั่วไป (และเป็นสิ่งจำเป็นโดย POSIX) มันเป็นจำนวนตัวอักษร แต่สำหรับเชลล์บางตัวเช่นdashที่ไม่ทราบว่ามีหลายไบต์ก็จะเป็นไบต์แทน

ด้วยmksh, คุณต้องการset -o utf8-mode(ในโลแคล UTF-8) เพื่อให้เข้าใจอักขระหลายไบต์:

$ string=€€€ bash -c 'echo "${#string}"'
3
$ string=€€€ dash -c 'echo "${#string}"'
9
$ string=€€€ mksh -c 'echo "${#string}"'
9
$ string=€€€ mksh -o utf8-mode -c 'echo "${#string}"'
3
$ locale charmap
UTF-8

หัวข้อecho Too longแตกต่างกันแต่แตกต่างกันภายใต้ประทุนจากecho 'Too long'
Steven Penny

และถ้าคุณเพิ่งจะพิมพ์เมื่อมัน "ยาวเกินไป" ฉันสามารถกระชับifตัวเลือกของฉันได้มากขึ้น:)

2
@StevenPenny, echo Too longผ่านสองอาร์กิวเมนต์ ( Tooและlong) ไปechoซึ่งechoผลคั่นด้วยช่องว่าง (และตามมาด้วยการขึ้นบรรทัดใหม่) ในขณะที่echo 'Too long'เราผ่านหนึ่งToo longอาร์กิวเมนต์echoซึ่งจะแสดงต่อไปโดยการขึ้นบรรทัดใหม่ ดังนั้นมันจึงเทียบเท่ากับฟังก์ชัน
Stéphane Chazelas
โดยการใช้ไซต์ของเรา หมายความว่าคุณได้อ่านและทำความเข้าใจนโยบายคุกกี้และนโยบายความเป็นส่วนตัวของเราแล้ว
Licensed under cc by-sa 3.0 with attribution required.