Làm cách nào để xóa tất cả các dòng trong một tệp bằng vi?


269

Làm cách nào để xóa tất cả các dòng trong một tệp bằng vi?

Hiện tại tôi làm điều đó bằng cách sử dụng một cái gì đó như thế này để xóa tất cả các dòng trong một tệp:

echo > test.txt

Làm thế nào tôi có thể xóa tất cả các dòng bằng cách sử dụng vi?

Lưu ý: Sử dụng ddkhông phải là một lựa chọn tốt. Có thể có nhiều dòng.


5
Tôi nghĩ rằng dG nên làm việc.
MadTux

11
@MadTux, chỉ khi bạn bắt đầu trên dòng đầu tiên. 1GdGsẽ làm việc từ bất cứ đâu.
Holloway

1
echo | test.txtkhông phải là một lệnh hợp lệ, trừ khi test.txtlà một tập lệnh thực thi. Tôi đoán bạn có nghĩa là echo >test.txtthay thế?
tripleee

Bạn nói đúng @tripleee
Lạnh

5
Lưu ý rằng không sử dụng vi, >test.txtlà đủ để cắt nó đến độ dài bằng không - không echocần thiết.
abligh

Câu trả lời:


473

trong viviệc phải làm

:1,$d

để xóa tất cả các dòng.

Lệnh :giới thiệu (và di chuyển con trỏ xuống dưới cùng).
Đây 1,$là một dấu hiệu cho biết dòng lệnh nào sau đây ( d) sẽ hoạt động. Trong trường hợp này, phạm vi từ dòng một đến dòng cuối cùng (được chỉ định bởi $, vì vậy bạn không cần biết số lượng dòng trong tài liệu).
Cuối cùng dlà viết tắt của các dòng chỉ định.

Có một hình thức ngắn hơn ( :%d) nhưng tôi thấy mình không bao giờ sử dụng nó. Có :1,$dthể dễ dàng "điều chỉnh" hơn, ví dụ như :4,$-2dchỉ để lại 3 dòng đầu tiên và 2 dòng cuối cùng, xóa phần còn lại.


9
Mẹo chuyên nghiệp. Không còn nữaESC+dd+dd+dd+dd+dd+dd+dd+dd+dd+dd+dd+dd+dd+dd+dd+dd...
lần

2
@ rdev5 thử .lần sau để lặp lại lệnh
Gazihan Alankus

169

Trong vi tôi dùng

:%d

Ở đâu

  • : bảo vi đi trong chế độ lệnh
  • % có nghĩa là tất cả các dòng
  • d : xóa bỏ

Trên dòng lệnh,

> test.txt

cũng sẽ làm

Có vấn đề gì với dd?

dd if=/dev/null of=test.txt

Ở đâu

  • /dev/null là một tệp 0 byte đặc biệt
  • if là tập tin đầu vào
  • of là tập tin ouput

Tôi đã nghĩ rằng sử dụng ddtôi cần pess cho mỗi dòng trong hồ sơ.
Lạnh

Tốt Nó đơn giản hơn tôi mong đợi ...
Lạnh

11
Bạn cần phân biệt giữa ddlệnh vi (nghĩa của OP) và ddtiện ích mà bạn đưa ra một ví dụ về. Ngoài ra, > test.txtcó thể không hoạt động như mong đợi trong các shell không bash (ví dụ zsh).
tước

1
@depquid Oups! bây giờ tôi nghĩ về nó ...
Archemar

2
Hoặc : >test.txtchỉ dài hơn một chút.
tripleee

53

Tôi khuyên bạn chỉ nên làm điều này (nên hoạt động trong mọi vỏ tương thích POSIX):

> test.txt

Nếu bạn thực sự muốn làm điều đó với vi, bạn có thể làm:

  • 1G (đi đến dòng đầu tiên)
  • dG (xóa đến dòng cuối cùng)

30
@Cold: ... một lần?
Chris Xuống

5
Gđại diện cho dòng cuối cùng. Nếu bạn đang ở dòng đầu tiên ( gg), hãy dGbảo vi xóa tất cả các dòng từ dòng hiện tại (dòng đầu tiên) đến dòng cuối cùng. Vì vậy, bạn làm điều đó trong một shot.
unxnut

6
gglà vim cụ thể. Đó là 1Gtrong truyền thống vi.
Stéphane Chazelas

1
Cú pháp shell của bạn phụ thuộc vào cấu hình cho một số shell. Cả shell tương tác bash và zsh (zsh theo mặc định) đều có thể đợi đầu vào trên STDIN sau khi nhận lệnh đó và cần thêm <CTRL> + D để thực sự xóa tệp. Khả năng chạy cũng phụ thuộc vào cài đặt CLOBBER. >| test.txt < /dev/nullmạnh hơn một chút vì nó sẽ luôn ghi đè tệp và tránh chờ đầu vào trên các thiết bị đầu cuối tương tác.
Caleb

1
@Caleb: Như tôi đã nói, trong bất kỳ trình bao tuân thủ POSIX nào . :-) Cả hai tình huống này đều là khiếu nại POSIX.
Chris Xuống

28

Nếu con trỏ của bạn ở dòng đầu tiên (nếu không, hãy nhập: gghoặc 1G), sau đó bạn chỉ có thể sử dụng dG. Nó sẽ xóa tất cả các dòng từ dòng hiện tại đến cuối tập tin. Vì vậy, để đảm bảo rằng bạn sẽ xóa tất cả các dòng khỏi tệp, bạn có thể trộn cả hai lại với nhau, đó là: ggdG(trong khi ở chế độ lệnh).

Hoặc %dtrong chế độ Ex, ví dụ dòng lệnh : vim +%d foo.bar.

Liên quan: Làm cách nào tôi có thể xóa trong VIM tất cả văn bản từ dòng hiện tại đến cuối tệp?


3
+1 vì tiện dụng hơn: 1, $ d. Dù sao, không phải là ngón tay của chúng ta không có dây để gõ đại tràng mọi lúc, dù sao đi nữa;)
Aaron R.

2
Nâng cao. dGlà những gì tôi luôn luôn sử dụng.
bữa ăn trưa317

1
Tôi thấy đây ( ggdG) phương pháp dễ nhất trong vim. Lý do câu trả lời này không được nêu lên như những người khác là vì ggnó không tồn tại trong vi thuần?
thameera

27

Tôi là một anh chàng lười biếng, và tôi muốn giữ cho nó đơn giản. ggdGlà năm tổ hợp phím bao gồmShift

ggđi đến dòng đầu tiên trong tập tin, dlà sự khởi đầu của dđộng từ elete và Glà chuyển động để đi đến cuối tập tin. Nói một cách rõ ràng, nó đi đến phần đầu của tệp và xóa mọi thứ cho đến khi kết thúc ô.


rsrs. Tôi cũng lười biếng và sử dụng :$dhoặc :1,$dlà cách nhanh hơn (tôi viết ít ký tự hơn) kkk
Lạnh

3
:%dlà lựa chọn tốt, vì bạn chỉ sử dụng 5 tổ hợp phím theo cách đó.
TankorSmash

1
@TankorSmash gglà một vimlệnh, không phải vi.
kyrias

bắt tốt, lỗi của tôi
TankorSmash


5

Tôi luôn luôn sử dụng ggVG

  • gg nhảy đến đầu tập tin chỉnh sửa hiện tại
  • V(viết hoa v) sẽ chọn dòng hiện tại. Trong trường hợp này, dòng đầu tiên của tệp chỉnh sửa hiện tại
  • G(viết hoa g) sẽ nhảy đến cuối tập tin. Trong trường hợp này, vì tôi đã chọn dòng đầu tiên, Gsẽ chọn toàn bộ văn bản trong tệp này.

Sau đó, bạn có thể chỉ cần nhấn dhoặc xđể xóa tất cả các dòng.


Nếu bạn sử dụng dtheo chiều dọc, nó sẽ tự động áp dụng theo chiều dọc. dlxóa một ký tự bên phải, djví dụ xóa một dòng xuống.
TankorSmash

3

lưu ý rằng trong câu hỏi của bạn, hãy echo > test.txttạo một tệp có một dòng ngắt trong đó, không phải là một tệp trống.

Từ vỏ, xem xét sử dụng echo -n > test.txthoặc : > test.txt.

Mặc dù tôi thường sử dụng lệnh chỉnh sửa vi (tôi sử dụng ggdG), bạn cũng có thể gọi ra trình bao với tham chiếu đến tệp hiện tại như vậy:

:!:>%

Nó gần như ngắn gọn ggdG, nhưng khó nhập hơn và bạn cũng phải xác nhận rằng bạn muốn tải lại tệp đã sửa đổi, vì vậy tôi không đặc biệt khuyên dùng nó trong trường hợp này, nhưng biết cách sử dụng các lệnh shell từ vi như thế này là hữu ích.

phá vỡ nó:

  • : bắt đầu một lệnh vi
  • ! bắt đầu một lệnh shell
  • : Đây là một lệnh dựng sẵn shell với đầu ra trống
  • > chuyển hướng đầu ra
  • % vi thay thế bằng tên của tệp hiện tại

Tất nhiên, đề xuất :1,$dcũng là một điều tốt, và ngay khi tôi ở đó cũng có1GdG


:!:>%cũng nguy hiểm vì vikhông thoát tên tệp cho trình bao (không thực hiện khi chỉnh sửa tệp được gọi là $(reboot)ví dụ). Bạn sẽ cần một cái gì đó:call system(":>" . shellescape(expand("%")))
Stéphane Chazelas

3

Giải pháp khác:

truncate -s 0 file

Không thực sự đơn giản hơn >filenhưng OK.
phk

1
Có vẻ là một phương pháp tốt, nhưng mục tiêu đang thực hiện bằng cách sử dụng vi. Tks
Lạnh


-1

Bạn có thể sử dụng một mẹo để xóa một số lượng lớn các dòng. Đảm bảo bạn không ở chế độ chèn (nhấn ESC), sau đó nhập 1000dd.


1
Bạn nên bao gồm phần giải thích về những gì lệnh thực hiện / cách thức hoạt động (xóa 1000 dòng tiếp theo, không xóa tất cả các dòng nếu con trỏ không ở dòng đầu tiên).
sebasth

đây là lý do tại sao tôi gọi nó là một mánh khóe :)
Radu

-1

Tôi gõ ggđể đạt đến đỉnh của các dòng và sau đó làm a 100 dd. Điều này đưa con trỏ đến dòng biên tập hàng đầu và xóa 100 dòng từ đó. Bạn có thể phải điều chỉnh số lượng để thêm nhiều dòng nếu tệp dài hơn.


-1
> file.txt

Bạn thậm chí không phải mở vi trừ khi bạn thực sự muốn.


1
Xin chào và chào mừng đến với trang web trao đổi ngăn xếp U & L. Vui lòng xem lại trung tâm trợ giúp để biết thông tin về cách đăng trang web này tốt nhất. Chúng tôi muốn nuôi dưỡng các câu hỏi và câu trả lời độc đáo và thông tin trên trang web này. Câu trả lời của bạn giống hệt với các câu trả lời và nhận xét khác về bài đăng này. Vui lòng chỉnh sửa bài viết của bạn để trở thành một câu trả lời độc đáo và nhiều thông tin hơn xin vui lòng. Cảm ơn bạn!
kemotep

Bên cạnh đó, điểm của câu hỏi là ... "sử dụng vi"
Jeff Schaller

Tôi đã thử chính xác những gì bạn đề nghị. Tôi nhận được bash: > file.txt: command not found.
roaima

@roaima Bạn sẽ nhận được điều đó nếu bạn trích dẫn điều đó "> file.txt".
Kusalananda

1
@JeffSchaller : vi >file.txt ;-)
Kusalananda
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.