Mengganti nama file saat ini di Vim

392

Bagaimana saya harus mengganti nama file saya saat ini di Vim?

Sebagai contoh:

  • Saya sedang mengedit person.html_erb_spec.rb
  • Saya ingin namanya diganti menjadi person.haml_spec.rb
  • Saya ingin terus mengedit person.haml_spec.rb

Bagaimana saya bisa melakukan ini dengan anggun?

Sam Saffron
sumber

Jawaban:

87

Ada sedikit plugin yang memungkinkan Anda melakukan ini.

innaM
sumber
9
Versi Rename.vim yang diperbarui ini menangani CWD dengan benar - selalu menyimpan file dalam direktori yang asli.
sickill
48
T: "orang aneh sosiopat apa yang memberi spasi pada nama dir?" - A: orang yang memulai proyek sejak lama yang sekarang menjadi bos Anda ... dipromosikan keluar dari pengkodean ke bidang keahliannya yang sebenarnya: mengikuti mode pengembangan metodologi dan memaksanya dalam tim.
Stabledog
3
@AaronMahan Saya telah memperbaiki Rename2.vim (mengabaikan versi DelvarWorld yang lebih pintar tapi lebih kompleks) untuk memungkinkan spasi di jalur dan bercabang di sini: github.com/aehlke/vim-rename3 Jangan ragu untuk mengirimkan permintaan tarik untuk fungsionalitas yang bahkan lebih cerdas!
aehlke
4
@Stabledog Microsoft, rupanya. Program Files (x86). Setiap saat direktori ini perlu dikerjakan harus dibungkus dengan tanda kutip. Yang mana, banyak.
JackHasaKeyboard
5
@JackHasaKeyboard: +10. "Program Files (x86)" memenangkan semua "Nama Direktori Terburuk Sepanjang Masa dalam Sistem Operasi yang Tidak memiliki Symlink." :)
Stabledog
451

Perintah itu dipanggil :saveas, tetapi sayangnya itu tidak akan menghapus file lama Anda, Anda harus melakukannya secara manual. lihat :help saveasuntuk info lebih lanjut.

EDIT:

Sebagian besar instalasi vim memiliki file explorer terintegrasi, yang dapat Anda gunakan untuk operasi tersebut. Coba :Exploredalam mode perintah (saya benar-benar akan memetakannya ke tombol fungsi, ini sangat berguna). Anda dapat mengganti nama file dengan Ratau menghapusnya D, misalnya. Tetapi menekan <F1>explorer akan memberi Anda gambaran yang lebih baik.

soulmerge
sumber
6
Saya tidak berpikir itu canggung dibandingkan dengan editor lain di mana Anda biasanya tidak dapat memindahkan file. Alih-alih, Anda harus membuka pengelola file pilihan Anda, mengganti nama file, dan kembali ke editor Anda. Jika Anda beruntung, Anda harus keluar dan memulai kembali editor Anda jika tidak mendapat pemberitahuan perubahan namafile.
Rafael Bugajewski
130
Anda mungkin juga menyukai: Seks (singkatan untuk split explore :-))
Peter Jankuliak
6
Juga,: e akan membuka penjelajahan di panel saat ini. Kurang mengasyikkan daripada: Seks tetapi lebih efisien;).
Josh
56
Untuk pemberani, vertikal: Seks adalah: Vex.
hobbes3
5
@ Josh: E bekerja untuk saya,: e tidak bekerja untuk saya. Saya menggunakan: e untuk mengedit file lain di jendela yang sama.
omar
159

Jika Anda menggunakan git dan sudah memiliki plugin tpope's fugitive.vim maka cukup:

:Gmove newname

Ini akan:

  1. Ganti nama file Anda di disk.
  2. Ganti nama file dalam git repo.
  3. Muat ulang file ke buffer saat ini.
  4. Pertahankan urungkan riwayat.

Jika file Anda belum ditambahkan ke repo git maka pertama-tama tambahkan:

:Gwrite
ISQ
sumber
4
Air mata keluar dari mataku. Jawaban sempurna!
Farid Nouri Neshat
3
Saya mengorbankan dua kambing untuk menghormati jawaban ini! Tapi saya punya masalah kecil dengan itu, karena Anda harus mengetikkan jalur dari akar pohon yang bekerja; dan ini sering menjadi agak panjang dalam proyek apa pun. Apakah ada solusi untuk ini?
xor
1
Itu keren! Saya terus menemukan hal-hal baru yang bisa dilakukan buron.
Rich Churcher
8
@xxor: seperti yang disebutkan dalam jawaban Mesco, Anda dapat menggunakan Ctrl + R% untuk memasukkan nama file saat ini, yang kemudian dapat diedit.
deltab
4
Untuk menggabungkan beberapa komentar di sini: :Gmovememerlukan jalur relatif untuk nama file baru. Cara yang bagus untuk melakukan ini adalah dengan mengetik :Gmove <ctrl-r>%yang menambahkan path / nama file saat ini.
shmup
80

Saya melakukannya dengan plugin NERDTree:

:NERDTreeFind

lalu tekan m

Untuk mengganti nama, Anda dapat memilih (m)ove the current nodedan mengubah nama file. Juga ada opsi seperti hapus, salin, pindahkan, dll ...

woto
sumber
1
Anda tahu, itulah cara utama saya mengubah nama barang belakangan ini
Sam Saffron
2
Yang ini bekerja dengan sangat baik. Pasti merekomendasikannya.
Matt Setter
Saya suka ide itu. Ini akan menjadi metode perubahan nama file utama saya sekarang.
SLN
72
  • Tulis file saat mengedit - :w newname- untuk membuat salinan.
  • Mulai mengedit salinan baru - :e#.
  • (Opsional) hapus salinan lama - :!rm oldname.

Pada Windows, langkah ke-3 opsional berubah sedikit:

  • (Secara opsional) hapus salinan Windows lama - :!del oldname.
Gimel
sumber
3
Saya menggunakan pendekatan ini sepanjang waktu, namun, downside adalah bahwa Anda kehilangan pohon
dibatalkan
7
Bagus. Rupanya Ctrl-6 melakukan hal yang sama seperti: e #
glenn Jackman
Anda juga dapat membuka direktori, memindahkan kursor ke file dan tekan "D" untuk menghapus file.
Peder
38
Cara yang lebih mudah adalah 1) ganti nama buffer saat ini :f newname2) simpan :w3) (opsional) !rm oldname. Keuntungannya adalah bahwa riwayat undo Anda dipertahankan.
kynan
3
:saveaslebih baik dalam hal itu, @rampion - dan melakukan apa yang ditulis @kynan.
lericson
36

Jika file sudah disimpan:

:!mv {file location} {new file location}
:e {new file location}

Contoh:

:!mv src/test/scala/myFile.scala src/test/scala/myNewFile.scala
:e src/test/scala/myNewFile.scala

Persyaratan Izin:

:!sudo mv src/test/scala/myFile.scala src/test/scala/myNewFile.scala

Simpan Sebagai:

:!mv {file location} {save_as file location}
:w
:e {save_as file location} 


Untuk Windows Tidak Diverifikasi

:!move {file location} {new file location}
:e {new file location}
Benjamin
sumber
5
Setidaknya Anda bisa menjelaskan mengapa Anda memilih jawaban ini.
Benjamin
31

Saya akan merekomendasikan :Renamedari kasim tope untuk ini.

Ini juga mencakup banyak perintah praktis lainnya.

Perintah Rename didefinisikan sebagai berikut di dalamnya saat ini (periksa repo untuk setiap pembaruan!):

command! -bar -nargs=1 -bang -complete=file Rename :
  \ let s:file = expand('%:p') |
  \ setlocal modified |
  \ keepalt saveas<bang> <args> |
  \ if s:file !=# expand('%:p') |
  \   call delete(s:file) |
  \ endif |
  \ unlet s:file
Gavin Gilmour
sumber
31

Anda juga dapat melakukannya menggunakan netrw

Perintah explore membuka netrw di direktori file yang terbuka

:E

Pindahkan kursor ke atas file yang ingin Anda ganti namanya:

R

Ketikkan nama baru, tekan enter, tekan y.

Ben
sumber
Bagus! saya bahkan tidak tahu tentang netrw.
javadba
31

Pendek, aman, tanpa plugin:

:sav new_name
:!rm <C-R>#  // or !del <C-R># for windows

control+ R, #akan langsung diperluas ke file alternatif (jalur yang diedit sebelumnya di jendela saat ini) sebelum menekan Enter. Itu memungkinkan kami untuk meninjau apa yang sebenarnya akan kami hapus. Menggunakan pipa |dalam kasus seperti itu tidak aman, karena jika savgagal karena alasan apa pun, #masih akan menunjuk ke tempat lain (atau tidak ke mana-mana). Itu berarti !rm #atau delete(expand(#))mungkin menghapus file yang sama sekali berbeda! Jadi lakukan dengan tangan hati-hati atau gunakan skrip yang baik (mereka disebutkan dalam banyak jawaban di sini).

Pendidikan

... atau coba bangun sendiri fungsi / perintah / skrip. Mulai dari sth sederhana seperti:

command! -nargs=1 Rename saveas <args> | call delete(expand('#')) | bd #

setelah vimrc reload, ketikkan saja :Rename new_filename. Apa masalah dengan perintah ini?

Tes keamanan 1: Apa yang dilakukan :Renametanpa argumen?

Ya, itu menghapus file yang disembunyikan di '#'!

Solusi: Anda dapat menggunakan mis. kondisi atau trypernyataan seperti itu:

command! -nargs=1 Rename try | saveas <args> | call delete(expand('#')) | bd # | endtry

Tes keamanan 1: :Rename (tanpa argumen) akan menimbulkan kesalahan:

E471: Diperlukan argumen

Tes keamanan 2: Bagaimana jika nama akan sama dengan yang sebelumnya?

Tes keamanan 3: Bagaimana jika file akan berada di lokasi yang berbeda dari yang sebenarnya?

Perbaiki sendiri. Agar mudah dibaca, Anda dapat menulisnya dengan cara ini:

function! s:localscript_name(name):
  try
    execute 'saveas ' . a:name
    ...
  endtry
endfunction
command! -nargs=1 Rename call s:localscript_name(<f-args>)

catatan

  • !rm #lebih baik dari !rm old_name-> Anda tidak perlu mengingat nama lama

  • !rm <C-R>#lebih baik daripada !rm #ketika melakukannya dengan tangan -> Anda akan melihat apa yang sebenarnya Anda hapus (alasan keamanan)

  • !rmumumnya tidak terlalu aman ... mvke lokasi sampah lebih baik

  • call delete(expand('#'))lebih baik daripada perintah shell (OS agnostic) tetapi lebih lama untuk mengetik dan tidak mungkin untuk menggunakan control+R

  • try | code1 | code2 | tryend -> ketika kesalahan terjadi saat kode1, jangan jalankan kode2

  • :sav(atau :saveas) setara dengan :f new_name | w- lihat file_f - dan mempertahankan undo history

  • expand('%:p')memberikan seluruh jalur lokasi Anda ( %) atau lokasi file alternatif ( #)

Mesco
sumber
17
sav person.haml_spec.rb | call delete(expand('#'))
Maxim Kim
sumber
bagus! tidak tahu tentangcall delete(expand('#'))
Kyle Wild
10

Ada fungsi di .vimrc milik Gary Bernhardt yang menangani ini.

function! RenameFile()
let old_name = expand('%')
let new_name = input('New file name: ', expand('%'), 'file')
if new_name != '' && new_name != old_name
    exec ':saveas ' . new_name
    exec ':silent !rm ' . old_name
    redraw!
endif
endfunction
map <leader>n :call RenameFile()<cr>
Jezen Thomas
sumber
5
Hilangkan saya semua yang Anda suka. Setidaknya saya bisa mengganti nama file.
Jezen Thomas
Ini adalah jawaban yang bagus, tidak perlu plugin tambahan.
wpp
8
:!mv % %:h/new_name

Daftar %berisi nama file saat ini. '%:h'memperlihatkan direktori 'head' yang berisi file saat ini, mis .: %:hkembali /abc/defketika path lengkap file Andaabc/dev/my.txt

Yossarian42
sumber
7

Bagaimana dengan ini (ditingkatkan oleh saran Jake):

:exe "!mv % newfilename" | e newfilename
murftown
sumber
Hmmm, saya harus mengklarifikasi bahwa itu bekerja pada MacVim kemarin tapi saya sshed ke server dan mencobanya hari ini dan perintah ke-2 tampaknya tidak diperlakukan sebagai perintah usus besar ...
murftown
1
Sebenarnya sekarang tidak berfungsi di MacVim juga. Kembali ke papan gambar! :)
murftown
2
Seharusnya:exe "!mv % newfilename" | e newfilename
Jake
Terima kasih Jake, itu sedikit lebih baik daripada solusi saya. Diperbarui.
murftown
7

Vim memang memiliki renamefungsi, tetapi sayangnya itu tidak mempertahankan sejarah.

Cara agnostik OS termudah untuk mengubah nama file tanpa kehilangan riwayatnya adalah:

:saveas new_file_name
:call delete(expand('#:p'))

expand('#:p') mengembalikan path lengkap file yang lebih lama.

Gunakan :bd #jika Anda juga ingin menghapus file yang lebih lama dari daftar buffer.

Atau buat plugin

Jika Anda ingin menggunakan perintah cepat untuk mengganti nama file, tambahkan file baru di bawah ~ / .vim / plugin dengan konten berikut:

function! s:rename_file(new_file_path)
  execute 'saveas ' . a:new_file_path
  call delete(expand('#:p'))
  bd #
endfunction

command! -nargs=1 -complete=file Rename call <SID>rename_file(<f-args>)

Perintah ini Renameakan membantu Anda dengan cepat mengganti nama file.

Alex
sumber
: hapus panggilan ('<Cr> #') lebih mudah untuk ditulis.
MaikoID
7

Ada plugin yang jauh lebih besar yang disebut vim-kasim oleh Tim Pope yang mencakup fungsi rename serta beberapa barang lainnya (hapus, temukan, simpan semua, chmod, sudo edit, ...).

Untuk mengganti nama file di vim-kasim:

:Move filename.ext

Dibandingkan dengan rename.vim:

:rename[!] filename.ext

Menghemat beberapa penekanan tombol :)

sh78
sumber
Dan memang memiliki beberapa fungsi lain yang sangat berguna!
Pierre-Adrien Buisson
5

Untuk mengganti nama file yang ada tanpa menggunakan plugin Anda harus menggunakan perintah

:Explore

Perintah ini memungkinkan Anda menjelajahi file di direktori, menghapus atau mengganti nama file. daripada Anda harus menavigasi ke file yang diperlukan di explorer daripada mengetik Rperintah yang akan memungkinkan Anda untuk mengubah nama file

Наглый Спамер
sumber
3

Saya tidak tahu apakah ini metode "termudah", tetapi dengan asumsi Anda sudah menyimpan file Anda (: w) Saya akan memanggil shell (: sh) dan melakukan cp foo foo.bak sederhana Untuk kembali ke editor gunakan Ctrl-D / Exit. Daftar perintah vi editor yang berguna pada tautan ini

DBMarcos99
sumber
Ini akan menyalin file, bukan mengganti nama itu.
innaM
Ah - Saya salah membaca "Saya ingin melanjutkan mengedit person.haml_spec.rb" Buruk!
DBMarcos99
Saya kira Anda bisa:! cp foo foo.new lalu: e foo.new?
DBMarcos99
3

Anda juga dapat menggunakan: f diikuti oleh: w


sumber
3
Ini tidak menghapus file lama.
Keith Pinson
1

Skrip kecil ini tidak sempurna (tambahan carriage-return yang harus Anda tekan) tapi itu sudah selesai.

function Rename()
  let new_file_name = input('New filename: ')
  let full_path_current_file = expand("%:p")
  let new_full_path = expand("%:p:h")."/".new_file_name
  bd    
  execute "!mv ".full_path_current_file." ".new_full_path
  execute "e ".new_full_path
endfunction                                                                                                                                                                                                                                 

command! Rename :call Rename()
nmap RN :Rename<CR>
Jonas Geiregat
sumber
0

Cara lain adalah dengan menggunakan netrw, yang merupakan bagian asli dari vim.

:e path/to/whatever/folder/

Lalu ada opsi untuk dihapus, ganti nama, dll.

Berikut ini keymap untuk membuka netrw ke folder file yang sedang Anda edit:

map <leader>e :e <C-R>=expand("%:p:h") . '/'<CR><CR>
dechimp
sumber
0

:sav newfile | !rm #

Perhatikan bahwa itu tidak menghapus file lama dari daftar buffer. Jika itu penting bagi Anda, Anda dapat menggunakan yang berikut ini sebagai gantinya:

:sav newfile | bd# | !rm #

sitaktif
sumber