ถ้าฉันเขียน
#!/bin/bash
echo "foo"
หรือ
#!/bin/sh
echo "foo"
ทั้งสองให้ผลเหมือนกัน ผมเคยเห็นบางสคริปต์ที่เริ่มต้นด้วยหรือ#!/bin/sh
#!/bin/bash
มีความแตกต่างระหว่างพวกเขาหรือไม่?
ถ้าฉันเขียน
#!/bin/bash
echo "foo"
หรือ
#!/bin/sh
echo "foo"
ทั้งสองให้ผลเหมือนกัน ผมเคยเห็นบางสคริปต์ที่เริ่มต้นด้วยหรือ#!/bin/sh
#!/bin/bash
มีความแตกต่างระหว่างพวกเขาหรือไม่?
คำตอบ:
bash
และsh
เป็นเปลือกหอยสองแบบ โดยทั่วไปbash
คือsh
มีคุณสมบัติมากขึ้นและไวยากรณ์ที่ดีกว่า คำสั่งส่วนใหญ่ทำงานเหมือนกัน แต่แตกต่างกัน
ต้องบอกว่าคุณควรตระหนักในระบบส่วนใหญ่จะมีการเชื่อมโยงสัญลักษณ์และจะไม่ก่อให้เกิด/bin/sh
sh
ใน Ubuntu /bin/sh
ที่ใช้ในการเชื่อมโยงไปยังbash
พฤติกรรมทั่วไปบนลินุกซ์ แต่ตอนนี้มีการเปลี่ยนแปลงที่จะเชื่อมโยงไปยังอีกที่เรียกว่าเปลือกประ ฉันจะใช้bash
เนื่องจากเป็นมาตรฐาน (หรืออย่างน้อยที่สุดจากประสบการณ์ของฉัน) ในความเป็นจริงแล้วปัญหาเกิดขึ้นเมื่อสคริปต์ทุบตีจะใช้#!/bin/sh
เพราะผู้สร้างสคริปต์สันนิษฐานว่าการเชื่อมโยงคือbash
เมื่อไม่จำเป็นต้องเป็น
สำหรับข้อมูลเพิ่มเติมhttp://man.cx/sh , http://man.cx/bash
/bin/sh
เคยเป็นเปลือกที่เรียกว่าเปลือกbourneย้อนกลับไปในปี 1977 ทุบตีเป็นเปลือกเข้ากันได้ / bin / sh ที่สามารถใช้เป็นทดแทนเปลือก bourne ที่เป็นไปตาม posix en.wikipedia.org/wiki/Bourne_shell
บน Linux และระบบที่คล้าย Unix อื่น ๆ คุณสามารถเลือกได้หลายเชลล์
เชลล์ไม่เพียงรับผิดชอบในการวาดพรอมต์เล็ก ๆ น้อย ๆ ของคุณ แต่เป็นการตีความคำสั่งของคุณโดยเฉพาะอย่างยิ่งถ้าคุณใส่ตรรกะที่ซับซ้อนเช่นไพพ์, เงื่อนไขและอื่น ๆ
bashเป็นเชลล์ทั่วไปที่ใช้เป็นเชลล์เริ่มต้นสำหรับผู้ใช้ระบบ Linux มันคือการสืบทอดทางวิญญาณของกระสุนอื่น ๆ ที่ใช้ในประวัติศาสตร์ Unix ชื่อของมันทุบตีเป็นตัวย่อของ Bourne-Again Shell เป็นการแสดงความเคารพต่อ Bourne shell ที่ถูกออกแบบมาเพื่อแทนที่แม้ว่ามันจะรวมเอาคุณสมบัติต่างๆจาก C Shell และ Korn Shell
มันทำงานตั้งแต่วันนี้/bin/bash
- ระบบใด ๆ ที่มี bash จะสามารถเข้าถึงได้ที่นี่
ไม่ใช่แค่ผู้ใช้ที่ใช้เปลือกหอย สคริปต์ ( เชลล์สคริปต์ ) จำเป็นต้องใช้เชลล์เพื่อแปลความหมาย เมื่อคุณเรียกใช้เชลล์สคริปต์ระบบของคุณต้องเริ่มกระบวนการเชลล์เพื่อรันสคริปต์ของคุณ
ปัญหาคือเชลล์ที่แตกต่างกันมีความแตกต่างกันเล็กน้อยระหว่างมันและเมื่อพูดถึงการรันสคริปต์มันอาจเป็นปัญหาจริง bashมีคุณสมบัติการเขียนสคริปต์จำนวนมากที่ไม่เหมือนใครในการทุบตีและไม่ใช่เชลล์อื่น ๆ ไม่เป็นไรถ้าคุณจะใช้ bash เพื่อเรียกใช้สคริปต์เหล่านี้ เชลล์อื่นอาจพยายามเลียนแบบ bash หรือเป็นไปตามมาตรฐาน POSIX ซึ่ง bash รองรับค่อนข้างดี (แม้ว่าจะเพิ่มส่วนขยายของมันเอง)
เป็นไปได้ที่จะระบุที่ด้านบนของเชลล์สคริปต์ที่เชลล์ควรรันด้วยการใช้ shebang สคริปต์อาจระบุ#!/bin/bash
ในบรรทัดแรกซึ่งหมายความว่าสคริปต์ควรรันด้วย bash เสมอแทนที่จะเป็นเชลล์อื่น
bin / sh /เป็นปฏิบัติการที่เป็นตัวแทนของเปลือกระบบ ที่จริงแล้วมันมักจะถูกนำไปใช้เป็นลิงค์สัญลักษณ์ที่ชี้ไปที่ปฏิบัติการสำหรับเชลล์ใดก็ตามที่เป็นเชลล์ระบบ เชลล์ของระบบเป็นชนิดของเชลล์เริ่มต้นที่สคริปต์ระบบควรใช้ ในลีนุกซ์ดิสทริบิวชั่นเป็นเวลานานซึ่งโดยปกติจะเป็นลิงก์สัญลักษณ์ไปยังbashดังนั้นมันจึงกลายเป็นรูปแบบการประชุมที่มักจะลิงค์ / bin / sh ไปยัง bash หรือเชลล์ที่ใช้ร่วมกันได้ อย่างไรก็ตามในช่วงสองสามปีที่ผ่านมา Debian (และ Ubuntu) ได้ตัดสินใจเปลี่ยนเชลล์ระบบจาก bash เป็นdash- เชลล์ที่คล้ายกัน - ทำลายด้วยประเพณีอันยาวนานใน Linux (ดี GNU) ของการใช้ bash สำหรับ / bin / sh Dash ถูกมองว่าเป็นเชลล์ที่เบากว่าและเร็วกว่ามากซึ่งเป็นประโยชน์ต่อความเร็วในการบูต (และสิ่งอื่น ๆ ที่ต้องการเชลล์สคริปต์จำนวนมากเช่นสคริปต์การติดตั้งแพ็กเกจ)
Dash นั้นเข้ากันได้ดีกับ bash โดยใช้มาตรฐาน POSIX เดียวกัน อย่างไรก็ตามมันไม่ได้ใช้ส่วนขยายเฉพาะของ bash มีสคริปต์ที่มีอยู่ซึ่งใช้#!/bin/sh
(เชลล์ระบบ) เป็น Shebang ของมัน แต่ต้องใช้ส่วนขยายเฉพาะของ bash ปัจจุบันนี้ถือว่าเป็นข้อผิดพลาดที่ควรได้รับการแก้ไขโดย Debian และ Ubuntu ซึ่งต้องการ / bin / sh เพื่อให้สามารถทำงานได้เมื่อชี้ไปที่เส้นประ
แม้ว่าเชลล์ระบบของ Ubuntu จะชี้ไปที่เส้นประ แต่เชลล์ล็อกอินของคุณในฐานะผู้ใช้ยังคงถูกทุบตีในขณะนี้ นั่นคือเมื่อคุณล็อกอินเข้าสู่เทอร์มินัลอีมูเลเตอร์ที่ใดก็ได้ใน Linux เชลล์ล็อกอินของคุณจะถูกทุบตี ความเร็วของการดำเนินการไม่ใช่ปัญหามากเมื่อเชลล์ใช้แบบโต้ตอบและผู้ใช้คุ้นเคยกับ bash (และอาจมีการปรับแต่งเฉพาะของ bash ในโฮมไดเร็กตอรี่ของพวกเขา)
สิ่งที่คุณควรใช้เมื่อเขียนสคริปต์
#!/bin/bash
หากสคริปต์ของคุณต้องมีคุณสมบัติการสนับสนุนจากการทุบตีการใช้งานเท่านั้น
แต่ถ้าเป็นไปได้ควรตรวจสอบให้แน่ใจว่าสคริปต์ของคุณเข้ากันได้กับ POSIX และใช้งาน#!/bin/sh
ซึ่งควรเชื่อถือได้อย่างแน่นอนชี้ไปที่เชลล์ระบบที่รองรับ POSIX ที่ต้องการในการติดตั้งใด ๆ
นอกจากนี้ในการตอบก่อนหน้านี้แม้ว่า/bin/sh
เป็น symbolic link ไป/bin/bash
, ไม่ได้โดยสิ้นเชิงเทียบเท่ากับ#!/bin/sh
#!/bin/bash
จากหน้าคนทุบตี (1) :
"ถ้า bash ถูกเรียกด้วยชื่อ sh มันจะพยายามเลียนแบบพฤติกรรมการเริ่มต้นของ sh รุ่นที่ผ่านมามากที่สุดเท่าที่จะทำได้ในขณะที่สอดคล้องกับมาตรฐาน POSIX เช่นกัน"
ตัวอย่างเช่นไวยากรณ์เฉพาะของ bash:
exec > >(tee logfile.txt)
ให้ข้อผิดพลาดในเชลล์ที่ขึ้นต้นด้วย#!/bin/sh
แม้จะมี sh-> bash symbolic link อยู่