Sự khác biệt giữa ls [13] và ls {1,3} là gì?


11

Tôi đã tạo ba tệp trong thư mục của mình bằng lệnh touch inv{1..3}.txt. Bây giờ tôi đã sử dụng hai lệnh và đầu ra của chúng khá giống nhau. Hai lệnh đó là ls inv[13].txtls {1,3}.txt.

Vậy hai cái này khác nhau như thế nào? Làm thế nào là dấu ngoặc vuông khác nhau so với niềng răng? Ngoài ra, tôi đã tìm kiếm "linux [..]", nhưng không thể tìm thấy bất cứ điều gì, vì vậy tôi có thể biết những gì những thứ này được gọi trong thuật ngữ linux không?

Cảm ơn


2
Tên của cái này là "mở rộng tên tệp" hoặc "globalbing".
Chỉ huy Byte

Cái nào trong số này là mở rộng tên tệp hoặc globalbing? Đây có phải là dấu ngoặc vuông ([..]) hay khung hoa ({..})?
posixKing

Câu trả lời:


14
  • {}được gọi là mở rộng cú đúp. Nó có hai dạng: {x..y}{x,y}, thay thế xybằng bất kỳ giá trị chữ cái hoặc số.

    Ở dạng đầu tiên, {x..y}sẽ được mở rộng cho tất cả các giá trị từ xđến y, bao gồm. Ví dụ, {2..5}sẽ được mở rộng để 2, 3, 4, 5.

    Ở dạng rõ ràng thứ hai, {x,y}sẽ được mở rộng thành x, y. Ví dụ, {2,5}sẽ được mở rộng đến 25.

    Nếu không thể mở rộng, mô hình được xử lý theo nghĩa đen, ví dụ như trong {a..3}.

    Điều quan trọng cần lưu ý là việc mở rộng dấu ngoặc sẽ được thực hiện (nếu có thể) bất kể đối sánh bất kỳ tệp nào, trong khi tạo / khớp tệp.

  • []được biết đến như là một mẫu mở rộng tên đường dẫn (hoặc globalbing). Không giống như mở rộng dấu ngoặc, bạn chỉ có thể sử dụng nó trong khi khớp tên tệp, nó sẽ được xử lý theo nghĩa đen nếu bạn sử dụng nó trong khi tạo tệp.

    Nó có hai hình thức: [xyz...][x-y].

    Ở dạng đầu tiên, nó sẽ khớp với bất kỳ ký tự đơn nào trong dấu ngoặc vuông riêng biệt Mỗi ký tự được xử lý riêng. Vì vậy, cho [25].txtnó sẽ phù hợp với một file có tên 2.txthoặc 5.txttrong thư mục hiện hành, trong khi đối với [245].txtnó sẽ phù hợp với bất kỳ tập tin có tên 2.txthay 4.txthay 5.txt.

    Ở dạng thứ hai, việc mở rộng phạm vi được thực hiện trước khi khớp riêng lẻ, nếu có thể được xử lý theo nghĩa đen. Vì vậy, đối [2-5]. txt, nó sẽ phù hợp với bất kỳ tập tin có tên 2.txthay 3.txthay 4.txthay 5.txt. Nếu phạm vi không thể được mở rộng, nó sẽ được xử lý theo nghĩa đen, ví dụ như trong trường hợp [a-3].txt.


Một sự khác biệt quan trọng về hành vi giữa hai điều này là khi có nhiều mẫu phù hợp hơn trong khi thực tế ít khớp hơn. Vì việc mở rộng dấu ngoặc được thực hiện bất kể là gì, nó sẽ hiển thị lỗi rằng (các) tệp nhất định không tồn tại trong khi mở rộng tên đường dẫn sẽ khớp với bất cứ điều gì có thể mà không có bất kỳ lỗi nào cho phần còn lại:

$ ls {1..4}.txt
ls: cannot access 4.txt: No such file or directory
1.txt  2.txt  3.txt

$ ls [1-4].txt
1.txt  2.txt  3.txt

Lưu ý về tính di động:

Các []nhà khai thác mở rộng tên đường dẫn được định nghĩa bởi POSIX vì thế linh động trong Bourne shell và các dẫn xuất.

Việc mở rộng niềng răng, {}không được xác định bởi POSIX do đó không khả dụng trong tất cả các hệ vỏ. Ví dụ: dash( shtrong Ubuntu) không có cái này. Nó được vay mượn từ cshvà sẽ làm việc trên vỏ nhất định ví dụ như bash, zsh, ksh93, fish. Hãy chắc chắn rằng shell bạn đang sử dụng hỗ trợ này trước khi thực hiện.


Thí dụ:

$ touch {1..3}.txt

$ ls {1..3}.txt
1.txt  2.txt  3.txt

$ ls {1,2,3}.txt
1.txt  2.txt  3.txt

$ ls {1..4}.txt
ls: cannot access 4.txt: No such file or directory
1.txt  2.txt  3.txt

$ ls {a..3}.txt
ls: cannot access {a..3}.txt: No such file or directory

$ ls [123].txt
1.txt  2.txt  3.txt

$ ls [1-3].txt
1.txt  2.txt  3.txt

$ ls [1-4].txt
1.txt  2.txt  3.txt

$ ls [a-3].txt
ls: cannot access [a-3].txt: No such file or directory

1
Người ta nên tránh dựa vào hành vi [ ]mở rộng khi không có kết quả khớp vì điều đó có thể khác nhau tùy thuộc vào cấu hình shell. Nếu bạn muốn sử dụng [hoặc ]trong một tên tệp, nó nên được trích dẫn trong các lệnh của bạn. Nó cũng đáng chú ý sự khác biệt giữa {13..79}[13-79]. Đầu tiên sẽ sản xuất tất cả các số trong khoảng từ 13đến 79, thứ hai sẽ phù hợp với nhân vật 1, 3, 4, 5, 6, 7, và 9.
kasperd

@kasperd Vâng, đó là những gì nullglob(hoặc tương tự) dành cho. Về sự [13-79]phù hợp, tôi nghĩ rằng tôi đã đề cập rõ ràng trong câu trả lời của mình về hành vi cho mỗi nhân vật của [] `.
heemayl

@heemayl Tôi nghĩ rằng cũng đáng để đề cập rằng hình thức `{1..3}` là bashism. Điều này sẽ không làm việc trong dấu gạch ngang. Tôi nghĩ kshcó tính năng này, nhưng không phải là hương vị hiện đại hơn, như mksh và pkdsh
Sergiy Kolodyazhnyy

@Serg Đã thêm ghi chú tính di động.
heemayl

7

Sự khác biệt chính giữa hai hình thức được minh họa ở đây:

$ ls inv[15].txt
inv1.txt
$ ls inv{1,5}.txt
ls: cannot access 'inv5.txt': No such file or directory
inv1.txt

inv[15].txtlà một quả địa cầu và sẽ mở rộng danh sách các tệp phù hợp trên hệ thống tệp của bạn. Đây là mở rộng tên đường dẫn .

inv{1,5}.txtmở rộng đến inv1.txtinv5.txtbất kể tập tin nào thực sự có trên hệ thống tập tin của bạn. Đây là mở rộng cú đúp .


Sự khác biệt chính khác là bạn có thể viết ba{con,tman}và không có dấu ngoặc vuông. IOW, mở rộng cú đúp không chỉ dành cho các ký tự đơn.
hobbs
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.