Câu trả lời:
Tương tự như tùy chọn đầu tiên nhưng bỏ qua dấu phân cách
ls -1 | paste -sd "," -
paste
được -
(đầu vào tiêu chuẩn) như mặc định, ít nhất là trên của tôi paste (GNU coreutils) 8.22
.
"\0"
, vì vậy paste -sd "\0" -
làm việc cho tôi!
EDIT : Đơn giản là " ls -m " Nếu bạn muốn dấu phân cách của bạn là dấu phẩy
Ah, sức mạnh và sự đơn giản!
ls -1 | tr '\n' ','
Thay đổi dấu phẩy " , " thành bất cứ điều gì bạn muốn. Lưu ý rằng điều này bao gồm một "dấu phẩy"
\n
trong đó, điều này cũng sẽ thay thế.
ls -1 | tr "\\n" "," | sed 's/\(.*\),/\1/'
sed
có thể hiệu quả hơn một chút với ký tự đánh dấu kết thúc:ls -1 | tr "\\n" "," | sed 's/,$//'; echo ''
sed
sau tr
dường như chỉ để loại bỏ biểu tượng cuối cùng có vẻ không hợp lý. Tôi đi vớils -1 | tr '\n' ',' | head -c -1
Điều này thay thế dấu phẩy cuối cùng bằng một dòng mới:
ls -1 | tr '\n' ',' | sed 's/,$/\n/'
ls -m
bao gồm các dòng mới ở ký tự chiều rộng màn hình (ví dụ thứ 80).
Chủ yếu là Bash (chỉ ls
là bên ngoài):
saveIFS=$IFS; IFS=$'\n'
files=($(ls -1))
IFS=,
list=${files[*]}
IFS=$saveIFS
Sử dụng readarray
(aka mapfile
) trong Bash 4:
readarray -t files < <(ls -1)
saveIFS=$IFS
IFS=,
list=${files[*]}
IFS=$saveIFS
Cảm ơn gniourf_gniourf cho các đề xuất.
mapfile
(Bash 4) là : mapfile -t files < <(ls -1)
. Không cần phải mân mê với IFS
. Và nó cũng ngắn hơn.
IFS
để tham gia các trường : saveIFS=$IFS; IFS=,; list=${files[*]}; IFS=$saveIFS
. Hoặc sử dụng một phương thức khác nếu bạn muốn một dấu phân cách có nhiều ký tự đó.
Tôi nghĩ rằng điều này là tuyệt vời
ls -1 | awk 'ORS=","'
ORS là "dấu tách bản ghi đầu ra", vì vậy bây giờ các dòng của bạn sẽ được nối bằng dấu phẩy.
" OR "
:)
Sự kết hợp của thiết lập IFS
và sử dụng "$*"
có thể làm những gì bạn muốn. Tôi đang sử dụng một lớp con nên tôi không can thiệp vào $ IFS của shell này
(set -- *; IFS=,; echo "$*")
Để nắm bắt đầu ra,
output=$(set -- *; IFS=,; echo "$*")
set
việc? Trông hơi giống voodoo với tôi. Nhìn nông cạn man set
cũng không cho tôi nhiều thông tin.
set
một loạt các đối số nhưng không có tùy chọn, nó sẽ đặt các tham số vị trí ($ 1, $ 2, ...). --
có để bảo vệ set
trong trường hợp đối số đầu tiên (hoặc tên tệp trong trường hợp này) xảy ra để bắt đầu bằng dấu gạch ngang. Xem mô tả của --
tùy chọn trong help set
. Tôi tìm thấy các tham số vị trí một cách thuận tiện để xử lý một danh sách các thứ. Tôi cũng có thể đã thực hiện điều này với một mảng:output=$( files=(*); IFS=,; echo "${files[*]}" )
type set
sẽ nói với bạn , set is a shell builtin
. Vì vậy, man set
sẽ không giúp đỡ, nhưng help set
sẽ làm. Trả lời: "- Gán mọi đối số còn lại cho các tham số vị trí."
set -- *
. Trì hoãn mở rộng *
một cấp độ, bạn có thể nhận được đầu ra chính xác mà không cần vỏ phụ : IFS=',' eval echo '"$*"'
. Tất nhiên điều đó sẽ thay đổi các tham số vị trí.
Phân tích cú pháp ls
nói chung không được khuyến khích , vì vậy cách tốt hơn là sử dụng find
, ví dụ:
find . -type f -print0 | tr '\0' ','
Hoặc bằng cách sử dụng find
và paste
:
find . -type f | paste -d, -s
Để tham gia nhiều dòng chung (không liên quan đến hệ thống tệp), hãy kiểm tra: ngắn gọn và di động , hãy tham gia vào dòng chữ trên dòng lệnh Unix .
Đừng phát minh lại bánh xe.
ls -m
Nó làm chính xác điều đó.
ls -m
và tr
xóa khoảng trắng sau dấu phẩy bạn sẽ làmls -m | tr -d ' '
sed 's/, /,/g
chỉ cần bash
mystring=$(printf "%s|" *)
echo ${mystring%|}
|
, @camh.
bash
printf
printf -v
sẽ chỉ hoạt động trong bash, trong khi câu trả lời được trình bày hoạt động trên nhiều loại vỏ.
|
, với điều kiện là cả hai dòng được sử dụng : printf -v mystring "%s|" * ; echo ${mystring%|}
.
Lệnh này dành cho người hâm mộ PERL:
ls -1 | perl -l40pe0
Ở đây 40 là mã bát phân bát phân cho không gian.
-p sẽ xử lý từng dòng và in
-l sẽ đảm nhiệm việc thay thế dấu vết \ n bằng ký tự ascii mà chúng tôi cung cấp.
-e là để thông báo cho PERL chúng tôi đang thực hiện dòng lệnh.
0 có nghĩa là thực sự không có lệnh để thực thi.
perl -e0 giống như perl -e ''
Có vẻ như các câu trả lời đã tồn tại.
Nếu bạn muốn
a, b, c
định dạng, hãy sử dụng ls -m
( câu trả lời của Tulains Córdova )
Hoặc nếu bạn muốn a b c
định dạng, hãy sử dụng ls | xargs
(phiên bản mô phỏng câu trả lời của Chris J )
Hoặc nếu bạn muốn bất kỳ dấu phân cách nào khác |
, hãy sử dụng ls | paste -sd'|'
(áp dụng câu trả lời của Artem )
Thêm vào đầu câu trả lời của Majkinetor, đây là cách xóa dấu phân cách dấu (vì tôi không thể chỉ nhận xét dưới câu trả lời của anh ấy):
ls -1 | awk 'ORS=","' | head -c -1
Chỉ cần loại bỏ bao nhiêu byte theo sau là dấu phân cách của bạn.
Tôi thích cách tiếp cận này vì tôi có thể sử dụng các dấu phân cách nhiều ký tự + các lợi ích khác của awk
:
ls -1 | awk 'ORS=", "' | head -c -2
BIÊN TẬP
Như Peter đã nhận thấy, số byte âm không được hỗ trợ trong phiên bản đầu MacOS gốc. Điều này tuy nhiên có thể dễ dàng sửa chữa.
Đầu tiên, cài đặt coreutils
. "Các tiện ích cốt lõi của GNU là các tiện ích thao tác tệp, vỏ và văn bản cơ bản của hệ điều hành GNU."
brew install coreutils
Các lệnh cũng được cung cấp bởi MacOS được cài đặt với tiền tố "g". Ví dụ gls
.
Khi bạn đã hoàn thành việc này, bạn có thể sử dụng ghead
có số byte âm hoặc tốt hơn, tạo bí danh:
alias head="ghead"
Cách quyến rũ,
sed -e ':a; N; $!ba; s/\n/,/g'
# :a # label called 'a'
# N # append next line into Pattern Space (see info sed)
# $!ba # if it's the last line ($) do not (!) jump to (b) label :a (a) - break loop
# s/\n/,/g # any substitution you want
Lưu ý :
Đây là tuyến tính phức tạp, chỉ thay thế một lần sau khi tất cả các dòng được nối vào Không gian mẫu của sed.
Câu trả lời của @ AnandRajaseka và một số câu trả lời tương tự khác, như ở đây , là O (n²), bởi vì sed phải thay thế mỗi khi một dòng mới được thêm vào Không gian mẫu.
Để so sánh,
seq 1 100000 | sed ':a; N; $!ba; s/\n/,/g' | head -c 80
# linear, in less than 0.1s
seq 1 100000 | sed ':a; /$/N; s/\n/,/; ta' | head -c 80
# quadratic, hung
Nếu phiên bản xargs của bạn hỗ trợ cờ -d thì nó sẽ hoạt động
ls | xargs -d, -L 1 echo
-d là cờ phân cách
Nếu bạn không có -d, thì bạn có thể thử cách sau
ls | xargs -I {} echo {}, | xargs echo
Các xargs đầu tiên cho phép bạn chỉ định dấu phân cách của bạn là dấu phẩy trong ví dụ này.
-d
chỉ định dấu phân cách đầu vào với GNU xargs, vì vậy sẽ không hoạt động. Ví dụ thứ hai thể hiện vấn đề tương tự như các giải pháp khác ở đây về dấu phân cách đi lạc ở cuối.
sed -e :a -e '/$/N; s/\n/\\n/; ta' [filename]
Giải trình:
-e
- biểu thị một lệnh được thực thi
:a
- là nhãn
/$/N
- xác định phạm vi khớp cho dòng mở rộng hiện tại và (N)
s/\n/\\n/;
- thay thế tất cả EOL bằng \n
ta;
- nhãn goto a nếu khớp thành công
Lấy từ blog của tôi .
Bạn có thể dùng:
ls -1 | perl -pe 's/\n$/some_delimiter/'
ls
tạo ra một đầu ra cột khi được kết nối với một đường ống, do đó, -1
là dự phòng.
Đây là một câu trả lời perl khác bằng cách sử dụng join
hàm dựng sẵn không để lại dấu phân cách:
ls | perl -F'\n' -0777 -anE 'say join ",", @F'
Việc tối nghĩa -0777
làm cho perl đọc tất cả các đầu vào trước khi chạy chương trình.
sed thay thế mà không để lại một dấu phân cách
ls | sed '$!s/$/,/' | tr -d '\n'
ls
có tùy chọn -m
phân định đầu ra bằng ", "
dấu phẩy và dấu cách.
ls -m | tr -d ' ' | tr ',' ';'
đường ống kết quả này tr
để loại bỏ khoảng trắng hoặc dấu phẩy sẽ cho phép bạn đặt lại kết quả tr
để thay thế dấu phân cách.
trong ví dụ của tôi, tôi thay thế dấu phân cách ,
bằng dấu phân cách;
thay thế ;
bằng bất cứ ký tự phân cách một ký tự nào bạn thích vì tr chỉ chiếm ký tự đầu tiên trong chuỗi bạn truyền vào dưới dạng đối số.
Phiên bản Perl nhanh với xử lý dấu gạch chéo:
ls -1 | perl -E 'say join ", ", map {chomp; $_} <>'
Giải thích:
ls -1 | paste -s -d ":" -
Không chắc chắn nếu đó là phổ quát với tất cả các phiên bản dán