Trong một thư mục, tôi có một loạt các *.html
tập tin. Tôi muốn đổi tên tất cả thành*.txt
Làm thế nào tôi có thể làm điều đó? Tôi sử dụng vỏ bash.
Trong một thư mục, tôi có một loạt các *.html
tập tin. Tôi muốn đổi tên tất cả thành*.txt
Làm thế nào tôi có thể làm điều đó? Tôi sử dụng vỏ bash.
Câu trả lời:
Để có giải pháp tốt hơn (chỉ có chức năng bash, trái ngược với các cuộc gọi bên ngoài), hãy xem một trong những câu trả lời khác .
Những điều sau đây sẽ làm và không yêu cầu hệ thống phải có rename
chương trình (mặc dù bạn thường xuyên có chương trình này trên hệ thống):
for file in *.html; do
mv "$file" "$(basename "$file" .html).txt"
done
EDIT: Như đã chỉ ra trong các bình luận, điều này không hoạt động đối với tên tệp có khoảng trắng trong đó mà không có trích dẫn thích hợp (hiện đã được thêm ở trên). Khi làm việc hoàn toàn trên các tệp của riêng bạn mà bạn biết không có khoảng trắng trong tên tệp, điều này sẽ hoạt động nhưng bất cứ khi nào bạn viết một cái gì đó có thể được sử dụng lại sau đó, đừng bỏ qua trích dẫn thích hợp.
ren *.a *.b
$()
cú pháp POSIX được chỉ định thay vì cú pháp backtick cũ. Cải thiện khả năng đọc và làm cho cú pháp ít mơ hồ hơn khi bạn có các ký tự cần phải được gạch chéo ngược để thoát thành chữ bên trong thay thế lệnh bằng cái sau.
Nếu sử dụng bash, không cần các lệnh bên ngoài như sed, tên cơ sở, đổi tên, expr, v.v.
for file in *.html
do
mv "$file" "${file%.html}.txt"
done
"${file%.*}.txt"
, nhưng điều này có thể gây nguy hiểm cho các tệp không có phần mở rộng.
$
bên trong niềng răng xoăn!
--
"toán tử": mv - "$ file" "$ {file% .html} .txt" Toán tử đó ngăn tên tệp bắt đầu bằng a '-' khỏi bị phân tích cú pháp bởi mv làm đối số.
rename 's/\.html$/\.txt/' *.html
làm chính xác những gì bạn muốn.
Điều này làm việc cho tôi trên OSX từ .txt đến .txt_bak
find . -name '*.txt' -exec sh -c 'mv "$0" "${0%.txt}.txt_bak"' {} \;
.txt
để .txt_bak
bạn chỉ phải tiếp nhau _bak
;)
.scss
thành .sass
(sau khi chuyển đổi tại chỗ):find . -name '*.scss' -exec sh -c 'mv "$0" "${0%.scss}.sass"' {} \;
Bạn muốn sử dụng rename
:
rename -S .html .txt *.html
Điều này thực hiện chính xác những gì bạn muốn - nó sẽ thay đổi phần mở rộng từ .html
thành .txt
cho tất cả các tệp phù hợp *.html
.
Lưu ý: Greg Hewgill chỉ ra chính xác đây không phải là nội dung bash; và là một lệnh Linux riêng biệt. Nếu bạn chỉ cần một cái gì đó trên Linux thì nó sẽ hoạt động tốt; Nếu bạn cần một cái gì đó đa nền tảng hơn thì hãy xem một trong những câu trả lời khác.
rename
chương trình không liên quan bash
và cũng không có sẵn trên tất cả các nền tảng. Tôi chỉ thấy nó trên Linux.
rename -S .html .text *.html
nơi -S
viết tắt của--subst-all
Đối với người dùng Ubuntu:
rename 's/\.html$/\.txt/' *.html
Dưới đây là một ví dụ về lệnh đổi tên:
rename -n ’s/\.htm$/\.html/’ *.htm
-N có nghĩa là đó là bản chạy thử và sẽ không thực sự thay đổi bất kỳ tệp nào. Nó sẽ hiển thị cho bạn một danh sách các tệp sẽ được đổi tên nếu bạn xóa -n. Trong trường hợp trên, nó sẽ chuyển đổi tất cả các tệp trong thư mục hiện tại từ phần mở rộng tệp của .htm sang .html.
Nếu đầu ra của lần chạy thử trên có vẻ ổn thì bạn có thể chạy phiên bản cuối cùng:
rename -v ’s/\.htm$/\.html/’ *.htm
-V là tùy chọn, nhưng nên bao gồm nó vì đây là bản ghi duy nhất bạn sẽ có các thay đổi được thực hiện bằng lệnh đổi tên như được hiển thị trong đầu ra mẫu bên dưới:
$ rename -v 's/\.htm$/\.html/' *.htm
3.htm renamed as 3.html
4.htm renamed as 4.html
5.htm renamed as 5.html
Phần khó ở giữa là phần thay thế Perl bằng các biểu thức chính quy, được tô sáng bên dưới:
rename -v ’s/\.htm$/\.html/’ *.htm
Câu hỏi này đề cập rõ ràng đến Bash, nhưng nếu bạn có sẵn ZSH thì nó khá đơn giản:
zmv '(*).*' '$1.txt'
Nếu bạn nhận được zsh: command not found: zmv
thì chỉ cần chạy:
autoload -U zmv
Và sau đó thử lại.
Nhờ bài viết gốc này cho lời khuyên về zmv.
Sau khi thu thập dữ liệu trang web của người khác, tôi đã kết thúc với hàng ngàn tệp bị thiếu phần mở rộng .html, trên một cây thư mục con rộng.
Để đổi tên tất cả trong một lần, ngoại trừ các tệp đã có phần mở rộng .html (hầu hết trong số chúng không có gì cả), điều này hiệu quả với tôi:
cd wwwroot
find . -xtype f \! -iname *.html -exec mv -iv "{}" "{}.html" \; # batch rename files to append .html suffix IF MISSING
Trong trường hợp của OP, tôi có thể sửa đổi một chút, chỉ đổi tên các tệp * .txt, như vậy:
find . -xtype f -iname *.txt -exec filename="{}" mv -iv ${filename%.*}.{txt,html} \;
Bị hỏng (hammertime!):
-iname * .txt
- Có nghĩa là xem xét các tệp CHỈ đã kết thúc bằng .txt
mv -iv "{}. {txt, html}" - Khi find vượt qua {} làm tên tệp, $ {filename%. *} trích xuất tên cơ sở của nó mà không có bất kỳ phần mở rộng nào để tạo tham số cho mv . bash lấy {txt, html} để viết lại thành hai tham số để lệnh cuối cùng chạy như sau:mv -iv "filename.txt" "filename.html"
Khắc phục sự cố cần thiết: xử lý khoảng trắng trong tên tệp
Các lệnhmmv
dường như để làm nhiệm vụ này rất có hiệu quả trên một số lượng lớn các tập tin (hàng chục ngàn người trong một giây). Ví dụ: để đổi tên tất cả .xml
các tệp thành .html
tệp, hãy sử dụng:
mmv ";*.xml" "#1#2.html"
những ;
sẽ phù hợp với con đường, *
sẽ phù hợp với tên tập tin, và chúng được gọi là #1
và #2
trong tên thay thế.
Câu trả lời dựa trên exec
hoặc đường ống quá chậm hoặc thất bại trên một số lượng rất lớn các tệp.
Thử cái này
rename .html .txt *.html
sử dụng:
rename [find] [replace_with] [criteria]
Một chút muộn để dự tiệc. Bạn có thể làm điều đó với xargs:
ls *.html | xargs -I {} sh -c 'mv $1 `basename $1 .html`.txt' - {}
Hoặc nếu tất cả các tệp của bạn nằm trong một số thư mục
ls folder/*.html | xargs -I {} sh -c 'mv $1 folder/`basename $1 .html`.txt' - {}
ls
. Lệnh này là vô lý: nó sử dụng một cách vô dụng với ls
, thay vì sử dụng trực tiếp toàn cầu. Điều này sẽ phá vỡ với tên tệp chứa khoảng trắng, dấu ngoặc kép và (do thiếu dấu ngoặc kép) ký tự toàn cầu.
Đây là một cách tốt để sửa đổi nhiều tiện ích mở rộng cùng một lúc:
for fname in *.{mp4,avi}
do
mv -v "$fname" "${fname%.???}.mkv"
done
Lưu ý: hãy cẩn thận ở kích thước tiện ích mở rộng giống nhau (???)
Đẹp & đơn giản!
find . -iname *.html -exec mv {} "$(basename {} .html).text" \;
Nếu bạn thích PERL, có một đoạn script PERL ngắn (ban đầu được viết bởi Larry Wall, người tạo ra PERL) sẽ thực hiện chính xác những gì bạn muốn ở đây: tips.webdesign10.com/files/rename.pl.txt .
Ví dụ của bạn, sau đây nên thực hiện các mẹo:
rename.pl 's/html/txt/' *.html
Tương tự như những gì đã được đề xuất trước đây, đây là cách tôi đã làm:
find . -name '*OldText*' -exec sh -c 'mv "$0" "${0/OldText/NewText}"' {} \;
Lần đầu tiên tôi xác nhận
find . -name '*OldText*' -exec sh -c 'echo mv "$0" "${0/OldText/NewText}"' {} \;
Một dòng, không có vòng lặp:
ls -1 | xargs -L 1 -I {} bash -c 'mv $1 "${1%.*}.txt"' _ {}
Thí dụ:
$ ls
60acbc4d-3a75-4090-85ad-b7d027df8145.json ac8453e2-0d82-4d43-b80e-205edb754700.json
$ ls -1 | xargs -L 1 -I {} bash -c 'mv $1 "${1%.*}.txt"' _ {}
$ ls
60acbc4d-3a75-4090-85ad-b7d027df8145.txt ac8453e2-0d82-4d43-b80e-205edb754700.txt
Thật không may, nó không tầm thường để làm điều đó. Bạn có thể cần một chút phép thuật expr.
for file in *.html; do echo mv -- "$file" "$(expr "$file" : '\(.*\)\.html').txt"; done
Loại bỏ tiếng vang một khi bạn hạnh phúc nó làm những gì bạn muốn.
Chỉnh sửa: basename
có thể dễ đọc hơn một chút cho trường hợp cụ thể này, mặc dù expr
nói chung là linh hoạt hơn.
Đây là những gì tôi đã sử dụng để đổi tên .edge
tập tin thành.blade.php
for file in *.edge; do mv "$file" "$(basename "$file" .edge).blade.php"; done
Hoạt động như quyến rũ.
Bạn cũng có thể tạo một hàm trong Bash, thêm nó vào .bashrc
hoặc một cái gì đó và sau đó sử dụng nó bất cứ nơi nào bạn muốn.
change-ext() {
for file in *.$1; do mv "$file" "$(basename "$file" .$1).$2"; done
}
Sử dụng:
change-ext css scss
Nguồn mã trong chức năng: https://stackoverflow.com/a/1224786/6732111
Đổi tên phần mở rộng tệp cho tất cả các tệp trong thư mục hiện tại và thư mục con mà không có gói nào khác (chỉ sử dụng tập lệnh shell):
Tạo một tập lệnh shell rename.sh
trong thư mục hiện tại với đoạn mã sau:
#!/bin/bash
for file in $(find . -name "*$1"); do
mv "$file" "${file%$1}$2"
done
Chạy nó bằng cách ./rename.sh .old .new
.
Ví dụ. ./rename.sh .html .txt