$ * และ $ # ใน Linux คืออะไร


82

ตัวแปรสภาพแวดล้อมต่อไปนี้ใน Linux หมายถึงอะไร

  1. $ * (เครื่องหมายดอลลาร์ตามด้วยเครื่องหมายดอกจัน) คืออะไร
  2. อะไรคือ $ # (เครื่องหมายดอลลาร์ถัดจากเครื่องหมายแฮช / เครื่องหมายหมายเลข / octothorpe / ปอนด์)

คำตอบ:


115

จากที่นี่ :

$#    Stores the number of command-line arguments that 
      were passed to the shell program.
$?    Stores the exit value of the last command that was 
      executed.
$0    Stores the first word of the entered command (the 
      name of the shell program).
$*    Stores all the arguments that were entered on the
      command line ($1 $2 ...).
"$@"  Stores all the arguments that were entered
      on the command line, individually quoted ("$1" "$2" ...).

ดังนั้นโดยทั่วไป$#คือจำนวนของอาร์กิวเมนต์ที่กำหนดเมื่อสคริปต์ของคุณถูกดำเนินการ $*เป็นสตริงที่มีอาร์กิวเมนต์ทั้งหมด ตัวอย่างเช่น$1เป็นอาร์กิวเมนต์แรกและอื่น ๆ สิ่งนี้มีประโยชน์หากคุณต้องการเข้าถึงอาร์กิวเมนต์เฉพาะในสคริปต์ของคุณ

อย่างที่ไบรอันแสดงความคิดเห็นนี่เป็นตัวอย่างง่ายๆ หากคุณเรียกใช้คำสั่งต่อไปนี้:

./command -yes -no /home/username
  • $# = 3
  • $* = -yes -no /home/username
  • $@ = อาร์เรย์: {"-yes", "-no", "/home/username"}
  • $0= ./command, $1= -yesฯลฯ

สิ่งเหล่านี้เป็นส่วนหนึ่งของมาตรฐาน POSIXและควรได้รับการสนับสนุนจากเชลล์ที่เข้ากันได้ทั้งหมด สำหรับการอ้างอิงด้านล่างคือคำจำกัดความมาตรฐาน POSIX สำหรับพารามิเตอร์พิเศษแต่ละรายการ ไม่ทราบมีสามตัวแปรเพิ่มเติม: $-, และ$$$!

$@:

ขยายไปยังพารามิเตอร์ตำแหน่งโดยเริ่มจากหนึ่งพารามิเตอร์ เมื่อการขยายเกิดขึ้นภายในเครื่องหมายคำพูดคู่และเมื่อดำเนินการแยกฟิลด์ (ดูการแบ่งฟิลด์ ) แต่ละพารามิเตอร์ตำแหน่งจะขยายเป็นฟิลด์แยกโดยมีข้อกำหนดว่าการขยายตัวของพารามิเตอร์แรกจะยังคงเข้าร่วมกับส่วนเริ่มต้นของ คำเดิม (สมมติว่าพารามิเตอร์แบบขยายถูกฝังอยู่ภายในคำ) และการขยายตัวของพารามิเตอร์สุดท้ายจะยังคงเชื่อมต่อกับส่วนสุดท้ายของคำเดิม หากไม่มีพารามิเตอร์ตำแหน่งการขยายตัวของ '@' จะสร้างเขตข้อมูลเป็นศูนย์แม้ว่า '@' จะถูกยกมาเป็นสองครั้ง

$*:

ขยายไปยังพารามิเตอร์ตำแหน่งโดยเริ่มจากหนึ่งพารามิเตอร์ เมื่อการขยายเกิดขึ้นภายในสตริงที่มีเครื่องหมายคำพูดคู่ (ดูที่เครื่องหมายคำพูดคู่ ) มันจะขยายไปยังเขตข้อมูลเดียวที่มีค่าของแต่ละพารามิเตอร์คั่นด้วยอักขระตัวแรกของตัวแปร IFS หรือโดยถ้า IFS ไม่ได้ตั้งค่า หาก IFS ถูกตั้งค่าเป็นสตริงที่ว่างเปล่าสิ่งนี้จะไม่เทียบเท่ากับการยกเลิกการตั้งค่า ไม่มีอักขระตัวแรกดังนั้นค่าพารามิเตอร์จึงถูกต่อกัน

$#:

ขยายเป็นจำนวนทศนิยมของพารามิเตอร์ตำแหน่ง ชื่อคำสั่ง (พารามิเตอร์ 0) จะไม่ถูกนับในจำนวนที่กำหนดโดย '#' เพราะเป็นพารามิเตอร์พิเศษไม่ใช่พารามิเตอร์ตำแหน่ง

$?:

ขยายเป็นสถานะทางออกทศนิยมของไปป์ไลน์ล่าสุด (ดูที่Pipelines )

$-:

(เครื่องหมายขีดคั่น) ขยายเป็นแฟล็กตัวเลือกปัจจุบัน (ชื่อตัวอักษรตัวเดียวตัดแบ่งเป็นสตริง) ตามที่ระบุไว้ในการเรียกใช้โดยคำสั่งในตัวพิเศษที่กำหนดไว้หรือโดยปริยายโดยเชลล์

$$:

ขยายเป็น ID กระบวนการฐานสิบของเชลล์ที่เรียกใช้ ในเชลล์ย่อย (ดูที่Shell Execution Environment ) '$' จะขยายเป็นค่าเดียวกับเชลล์ปัจจุบัน

$!:

ขยายเป็น ID กระบวนการฐานสิบของคำสั่งพื้นหลังล่าสุด (ดูรายการ ) ที่ดำเนินการจากเชลล์ปัจจุบัน (ตัวอย่างเช่นคำสั่งพื้นหลังที่ดำเนินการจาก subshells จะไม่ส่งผลกระทบต่อมูลค่าของ "$!" ในสภาพแวดล้อมเชลล์ปัจจุบัน) สำหรับไพพ์ไลน์ ID กระบวนการคือคำสั่งสุดท้ายในไพพ์ไลน์

$0:

(ศูนย์) ขยายเป็นชื่อของเชลล์หรือเชลล์สคริปต์ ดูการดวลจุดโทษสำหรับคำอธิบายรายละเอียดของวิธีที่ใช้ชื่อนี้มีที่มา


1
พารามิเตอร์พิเศษเหล่านั้นเป็นจริงในเชลล์ที่ได้รับจาก Bourne ทั้งหมด (เช่น sh, bash, dash, ash, ksh, zsh)
Dennis Williamson

การแก้ไข: $*และ$#เป็น 1) ตัวแปรเชลล์ไม่ใช่ตัวแปรสภาพแวดล้อม 2) มาตรฐาน (ส่วนหนึ่งของข้อมูลจำเพาะ POSIX)
grawity

3
นอกจากนี้โปรดสังเกตว่า"$@"มีการเขียนหลายครั้งเป็น${1+"$@"}(สำหรับเหตุผลด้านการพกพา) ดูstackoverflow.com/questions/743454/…สำหรับคำอธิบาย
hlovdal

เนื่องจาก 'ชื่อคำสั่ง (พารามิเตอร์ 0) จะไม่ถูกนับ ... ' ในตัวอย่างด้านบนควรเป็น $ # = 2 เริ่มนับจาก 0
Josef Klimuk

0

$# แทนจำนวนอาร์กิวเมนต์:

[root@baymax ~]# set -- a
[root@baymax ~]# echo $#
1

[root@baymax ~]# set -- a b c
[root@baymax ~]# echo $#
3

2
ยินดีต้อนรับสู่ Super User ไซต์เป็นฐานความรู้ดังนั้นเจตนาคือคำตอบแต่ละข้อเสนอวิธีแก้ปัญหาสำหรับคำถามที่ไม่ได้มีส่วนร่วม นี่เป็นเพียงครึ่งหนึ่งของคำถามและข้อมูลได้รับการครอบคลุมอย่างดีในคำตอบก่อนหน้า
fixer1234
โดยการใช้ไซต์ของเรา หมายความว่าคุณได้อ่านและทำความเข้าใจนโยบายคุกกี้และนโยบายความเป็นส่วนตัวของเราแล้ว
Licensed under cc by-sa 3.0 with attribution required.