การเปลี่ยนชื่อไฟล์ปัจจุบันใน Vim


392

ฉันจะเปลี่ยนชื่อไฟล์ปัจจุบันของฉันเป็นกลุ่มได้อย่างไร?

ตัวอย่างเช่น:

  • ฉันกำลังแก้ไข person.html_erb_spec.rb
  • ฉันต้องการเปลี่ยนชื่อเป็น person.haml_spec.rb
  • ฉันต้องการแก้ไขต่อไป person.haml_spec.rb

ฉันจะทำสิ่งนี้อย่างสง่างามได้อย่างไร?

คำตอบ:


87

มีปลั๊กอินเล็กน้อยที่ให้คุณทำเช่นนี้


9
Rename.vim เวอร์ชันที่อัปเดตนี้จัดการ CWD อย่างถูกต้อง - บันทึกไฟล์ในไดเรกทอรีเดิมเสมอ
sickill

48
ถาม: "สิ่งแปลก ๆ ทางสังคมวิทยาแบบไหนที่ใส่ช่องว่างในชื่อ dir?" - A: คนที่เริ่มโครงการเมื่อนานมาแล้วซึ่งตอนนี้เป็นเจ้านายของคุณ ... เลื่อนขั้นจากการเขียนโค้ดลงในความเชี่ยวชาญที่แท้จริงของเขา
Stabledog

3
@AaronMahan ฉันได้แก้ไข Rename2.vim (ไม่สนใจรุ่น DelvarWorld ที่ฉลาดกว่า แต่ซับซ้อนกว่า) เพื่ออนุญาตให้มีช่องว่างในเส้นทางและแยกไว้ที่นี่: github.com/aehlke/vim-rename3อย่าลังเลที่จะส่งคำขอดึงสำหรับฟังก์ชั่นที่ชาญฉลาดยิ่งขึ้น!
aehlke

4
@Stabledog Microsoft เห็นได้ชัดว่า Program Files (x86). เมื่อใดก็ตามที่ไดเรกทอรีนี้จะต้องทำงานกับมันจะต้องถูกห่อด้วยคำพูด ซึ่งเอ่อมาก
JackHasaKeyboard

5
@JackHasaKeyboard: +10 "Program Files (x86)" ชนะชื่อไดเรกทอรีที่แย่ที่สุดตลอดกาลในระบบปฏิบัติการที่ไม่มี Symlinks :)
Stabledog

451

คำสั่งนั้นเรียกว่า:saveasแต่น่าเสียดายที่มันจะไม่ลบไฟล์เก่าของคุณคุณจะต้องทำด้วยตนเอง ดู:help saveasข้อมูลเพิ่มเติม

แก้ไข:

การติดตั้งเป็นกลุ่มส่วนใหญ่มีตัวสำรวจไฟล์รวมซึ่งคุณสามารถใช้สำหรับการดำเนินการดังกล่าว ลอง:Exploreในโหมดคำสั่ง (จริงๆแล้วฉันจะแมปที่ฟังก์ชั่นคีย์มันมีประโยชน์มาก ) คุณสามารถเปลี่ยนชื่อไฟล์ด้วยRหรือลบออกด้วยDเช่น แต่การกดปุ่ม<F1>สำรวจจะให้ภาพรวมที่ดีขึ้น


6
ฉันไม่คิดว่ามันน่าแปลกใจเมื่อเทียบกับบรรณาธิการอื่น ๆ ที่ปกติคุณไม่สามารถย้ายไฟล์ได้ แต่คุณต้องไปที่ตัวจัดการไฟล์ที่คุณเลือกเปลี่ยนชื่อไฟล์และกลับไปที่ตัวแก้ไขของคุณ หากคุณโชคดีคุณต้องเลิกและเริ่มแก้ไขใหม่หากไม่ได้รับการแจ้งเตือนการเปลี่ยนชื่อไฟล์
Rafael Bugajewski

130
คุณอาจชอบ: Sex (ชวเลขเพื่อแยกสำรวจ :-))
Peter Jankuliak

6
นอกจากนี้: e จะเปิดสำรวจในบานหน้าต่างปัจจุบัน น่าตื่นเต้นน้อยกว่า: เพศ แต่มีประสิทธิภาพมากกว่า;)
Josh

56
สำหรับความกล้าหาญแนวตั้ง: เพศคือ: Vex
hobbes3

5
@Josh: E ใช้งานได้สำหรับฉัน: e ใช้งานไม่ได้สำหรับฉัน ฉันใช้: e เพื่อแก้ไขไฟล์อื่นในหน้าต่างเดียวกัน
omar

159

หากคุณใช้คอมไพล์และมีปลั๊กอินของ tpope fugitive.vim อยู่แล้วเพียง:

:Gmove newname

นี่จะ:

  1. เปลี่ยนชื่อไฟล์ของคุณบนดิสก์
  2. เปลี่ยนชื่อไฟล์ใน git repo
  3. โหลดไฟล์ลงในบัฟเฟอร์ปัจจุบันอีกครั้ง
  4. รักษาประวัติเลิกทำ

หากไฟล์ของคุณยังไม่ถูกเพิ่มลงใน repo git ให้เพิ่มไฟล์ก่อน:

:Gwrite

4
น้ำตาไหลออกมาจากดวงตาของฉัน คำตอบที่สมบูรณ์แบบ!
Farid Nouri Neshat

3
ฉันเสียสละแพะสองตัวเพื่อเป็นเกียรติแก่คำตอบนี้! แต่ฉันมีปัญหาเล็กน้อยกับมันเพราะคุณต้องพิมพ์เส้นทางจากรากของต้นไม้ทำงาน และสิ่งนี้มักจะค่อนข้างยาวในโครงการใด ๆ มีวิธีแก้ปัญหานี้หรือไม่?
xor

1
เยี่ยมมาก! ฉันค้นหาสิ่งใหม่ ๆ ที่ผู้ลี้ภัยสามารถทำได้
Rich Churcher

8
@ xxxor: ดังที่ได้กล่าวไว้ในคำตอบของ Mesco คุณสามารถใช้ Ctrl + R% เพื่อแทรกชื่อไฟล์ปัจจุบันซึ่งสามารถแก้ไขได้
deltab

4
หากต้องการรวมความคิดเห็นเล็กน้อยที่นี่: :Gmoveต้องใช้พา ธ สัมพัทธ์สำหรับชื่อไฟล์ใหม่ วิธีที่ดีในการทำเช่นนี้คือการพิมพ์:Gmove <ctrl-r>%ที่ผนวกเส้นทาง / ชื่อไฟล์ปัจจุบัน
shmup

80

ฉันทำมันด้วยปลั๊กอิน NERDTree:

:NERDTreeFind

จากนั้นกด m

ในการเปลี่ยนชื่อคุณสามารถเลือก(m)ove the current nodeและเปลี่ยนชื่อไฟล์ นอกจากนี้ยังมีตัวเลือกเช่นลบคัดลอกย้าย ฯลฯ ...


1
คุณรู้ไหมว่านั่นคือวิธีหลักที่ฉันเปลี่ยนชื่อสิ่งของทุกวันนี้
Sam Saffron

2
อันนี้ใช้ได้ดีจริงๆ แนะนำอย่างแน่นอน
แมตต์ Setter

รักความคิด นี่จะเป็นวิธีเปลี่ยนชื่อไฟล์ของฉันตอนนี้
SLN

72
  • เขียนไฟล์ขณะแก้ไข - :w newname- เพื่อสร้างสำเนา
  • เริ่มต้นการแก้ไขสำเนาใหม่ :e#-
  • (เลือก) เอาชุดเก่า :!rm oldname-

บน Windows ขั้นตอนที่ 3 ทางเลือกจะเปลี่ยนแปลงเล็กน้อย:

  • (เลือก) ลบสำเนาของ Windows เก่า :!del oldname-

3
ฉันใช้วิธีนี้ตลอดเวลา แต่ข้อเสียคือคุณสูญเสียต้นไม้ที่เลิกทำดังนั้นคุณจึงไม่สามารถเลิกทำสิ่งใด ๆ ก่อน: e
rampion

7
ดี เห็นได้ชัดว่า Ctrl-6 ทำเช่นเดียวกับ: e #
glenn jackman

คุณสามารถเปิดไดเรกทอรีย้ายเคอร์เซอร์ไปที่ไฟล์แล้วกด "D" เพื่อลบไฟล์
Peder

38
วิธีที่ตรงไปตรงมามากขึ้น IMHO คือ 1) เปลี่ยนชื่อบัฟเฟอร์ปัจจุบัน:f newname2) บันทึก:w3) !rm oldname(เลือก) ข้อดีคือประวัติการเลิกทำของคุณจะถูกเก็บรักษาไว้
kynan

3
:saveasดีกว่าในเรื่องนั้น @rampion - และทำในสิ่งที่ @ kynan เขียน
lericson

36

หากไฟล์ถูกบันทึกแล้ว:

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

ตัวอย่าง:

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

ข้อกำหนดการอนุญาต:

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

บันทึกเป็น:

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


สำหรับ Windows Unverified

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

5
อย่างน้อยคุณสามารถอธิบายได้ว่าทำไมคุณถึงลงคะแนนในคำตอบนี้
Benjamin

31

ฉันขอแนะนำ:Renameจากขันทีของ tpope สำหรับเรื่องนี้

นอกจากนี้ยังมีคำสั่งที่ใช้งานง่ายอื่น ๆ อีกมากมาย

คำสั่ง Rename มีการกำหนดไว้ดังต่อไปนี้ (ตรวจสอบ repo สำหรับการอัพเดทใด ๆ !):

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

31

คุณสามารถทำได้โดยใช้ netrw

คำสั่งสำรวจเปิด netrw ในไดเรกทอรีของไฟล์ที่เปิด

:E

เลื่อนเคอร์เซอร์ไปที่ไฟล์ที่คุณต้องการเปลี่ยนชื่อ:

R

พิมพ์ชื่อใหม่กด Enter กด y


ที่ดี! ฉันไม่ได้รู้เกี่ยวกับ netrw
javadba

31

สั้นปลอดภัยโดยไม่ต้องใช้ปลั๊กอิน:

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

control+ R, #ทันทีจะขยายไปสู่การสำรองไฟล์ (เส้นทางแก้ไขก่อนหน้านี้ในหน้าต่างปัจจุบัน) Enterก่อนที่จะกด ที่ช่วยให้เราตรวจสอบสิ่งที่เรากำลังจะลบ การใช้ไพพ์|ในกรณีเช่นนี้ไม่ปลอดภัยเพราะหากsavล้มเหลวไม่ว่าด้วยเหตุผลใดก็ตาม#จะยังคงชี้ไปที่อื่น (หรือไม่มีอะไรเลย) นั่นหมายถึง!rm #หรือdelete(expand(#))อาจลบไฟล์ที่แตกต่างอย่างสิ้นเชิง! ดังนั้นให้ทำด้วยมืออย่างระมัดระวังหรือใช้สคริปต์ที่ดี (มีการกล่าวถึงในคำตอบมากมายที่นี่)

เกี่ยวกับการศึกษา

... หรือลองสร้างฟังก์ชั่น / คำสั่ง / สคริปต์ด้วยตัวเอง เริ่มต้นจาก sth ง่ายๆเช่น:

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

หลังจาก vimrc :Rename new_filenameโหลดเพียงชนิด ปัญหาของคำสั่งนี้คืออะไร?

การทดสอบความปลอดภัย 1:ไม่มีอะไร:Renameโต้แย้ง

ใช่มันจะลบไฟล์ที่ซ่อนอยู่ใน '#'!

การแก้ไข: คุณสามารถใช้เช่น เงื่อนไขหรือtryคำสั่งเช่นนั้น:

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

การทดสอบความปลอดภัย 1: :Rename (โดยไม่มีอาร์กิวเมนต์) จะทำให้เกิดข้อผิดพลาด:

E471: ต้องการอาร์กิวเมนต์

การทดสอบความปลอดภัย 2: จะทำอย่างไรถ้าชื่อจะเหมือนกันกับชื่อก่อนหน้า?

การทดสอบความปลอดภัยที่ 3: จะเกิดอะไรขึ้นถ้าไฟล์นั้นอยู่ในตำแหน่งที่แตกต่างจากของจริง?

แก้ไขด้วยตัวคุณเอง เพื่อความสะดวกในการอ่านคุณสามารถเขียนมันในลักษณะนี้:

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

บันทึก

  • !rm #ดีกว่า!rm old_name-> คุณไม่จำเป็นต้องจำชื่อเดิม

  • !rm <C-R>#ดีกว่า!rm #เมื่อทำด้วยมือ -> คุณจะเห็นสิ่งที่คุณลบจริง ๆ (เหตุผลด้านความปลอดภัย)

  • !rmโดยทั่วไปจะไม่ปลอดภัยมาก ... mvไปยังที่ตั้งถังขยะดีกว่า

  • call delete(expand('#'))ดีกว่าคำสั่ง shell (ผู้ไม่เชื่อเรื่องระบบปฏิบัติการ OS) แต่ใช้เวลานานกว่าในการพิมพ์และไม่สามารถใช้control+R

  • try | code1 | code2 | tryend -> เมื่อเกิดข้อผิดพลาดขณะที่ code1 อย่าเรียกใช้ code2

  • :sav(หรือ:saveas) เทียบเท่ากับ:f new_name | w- ดูfile_f - และเก็บรักษาประวัติการเลิกทำ

  • expand('%:p')ให้เส้นทางทั้งหมดของตำแหน่งของคุณ ( %) หรือตำแหน่งของไฟล์ทางเลือก ( #)



10

มีฟังก์ชั่นใน. vimrc ของ Gary Bernhardtที่จัดการสิ่งนี้

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>

5
ลงคะแนนฉันทั้งหมดที่คุณต้องการ อย่างน้อยฉันก็สามารถเปลี่ยนชื่อไฟล์ได้
Jezen Thomas

นี่เป็นคำตอบที่ยอดเยี่ยมไม่จำเป็นต้องใช้ปลั๊กอินเพิ่มเติม
wpp

8
:!mv % %:h/new_name

การลงทะเบียน%ประกอบด้วยชื่อของไฟล์ปัจจุบัน '%:h'แสดงไดเรกทอรี 'หัว' ที่มีไฟล์ปัจจุบันเช่น: %:hส่งคืน/abc/defเมื่อไฟล์เต็มพา ธ ของคุณคือabc/dev/my.txt


7

วิธีการเกี่ยวกับเรื่องนี้ (ปรับปรุงตามคำแนะนำของ Jake):

:exe "!mv % newfilename" | e newfilename

อืมมผมควรชี้แจงว่ามันทำงานใน MacVim เมื่อวานนี้ แต่ผม sshed ลงในเซิร์ฟเวอร์และพยายามวันนี้และคำสั่งที่ 2 ไม่ได้ดูเหมือนจะถือว่าเป็นคำสั่งลำไส้ใหญ่ ...
murftown

1
ตอนนี้ที่จริงแล้วมันไม่ทำงานบน MacVim เช่นกัน กลับไปที่กระดานวาดภาพ! :)
murftown

2
มันควรจะเป็น:exe "!mv % newfilename" | e newfilename
Jake

ขอบคุณ Jake ที่ดีกว่าโซลูชันของฉันเล็กน้อย Updated
ฆาตกรรม

7

เสียงเรียกเข้ามีrenameฟังก์ชั่น แต่น่าเสียดายที่มันไม่ได้เก็บประวัติ

วิธีที่ไม่เชื่อเรื่องพระเจ้าของระบบปฏิบัติการที่ง่ายที่สุดในการเปลี่ยนชื่อไฟล์โดยไม่สูญเสียประวัติจะเป็น:

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

expand('#:p') ส่งคืนพา ธ เต็มของไฟล์เก่า

ใช้:bd #หากคุณต้องการลบไฟล์เก่าออกจากรายการบัฟเฟอร์

หรือสร้างปลั๊กอิน

หากคุณต้องการใช้คำสั่งด่วนเพื่อเปลี่ยนชื่อไฟล์ให้เพิ่มไฟล์ใหม่ภายใต้ ~ / .vim / plugin ด้วยเนื้อหาต่อไปนี้:

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>)

คำสั่งRenameจะช่วยให้คุณเปลี่ยนชื่อไฟล์ได้อย่างรวดเร็ว


: call delete ('<Cr> #') เขียนได้ง่ายกว่า
MaikoID

7

มีปลั๊กอินขนาดใหญ่ที่เรียกว่าvim-eunuchโดย Tim Pope ที่มีฟังก์ชั่นการเปลี่ยนชื่อรวมถึงสินค้าอื่น (ลบค้นหาค้นหาบันทึกทั้งหมด chmod, sudo edit, ... )

ในการเปลี่ยนชื่อไฟล์ใน vim-eunuch:

:Move filename.ext

เปรียบเทียบกับ rename.vim:

:rename[!] filename.ext

บันทึกการกดแป้นบางครั้ง :)


และมันมีฟังก์ชั่นที่มีประโยชน์อื่น ๆ อีกมากมาย!
Pierre-Adrien Buisson

5

สำหรับการเปลี่ยนชื่อไฟล์ที่มีอยู่โดยไม่ใช้ปลั๊กอินคุณควรใช้คำสั่ง

:Explore

คำสั่งนี้อนุญาตให้คุณสำรวจไฟล์ in.directory ลบหรือเปลี่ยนชื่อไฟล์ กว่าที่คุณควรนำทางไปยังไฟล์ที่จำเป็นใน explorer กว่าRคำสั่งtype ซึ่งจะช่วยให้คุณเปลี่ยนชื่อไฟล์ได้


3

ฉันไม่รู้ว่านี่เป็นวิธีที่ "ง่ายที่สุด" หรือไม่ แต่สมมติว่าคุณได้บันทึกไฟล์ของคุณแล้ว (: w) ฉันจะเรียกใช้เชลล์ (: sh) และทำ cp foo foo.bak ง่ายๆเพื่อกลับไปที่เครื่องมือแก้ไข ใช้ Ctrl-D / Exit รายการที่เป็นประโยชน์ของคำสั่งเอดิเตอร์ vi บนลิงก์นี้


นี่จะเป็นการคัดลอกไฟล์ไม่ใช่เปลี่ยนชื่อ
innaM

อ่า - ฉันอ่านผิด "ฉันต้องการแก้ไขคนต่อไปhaml_spec.rb" แย่จัง!
DBMarcos99

ฉันคิดว่าคุณทำได้:! cp foo foo.new แล้ว: e foo.new?
DBMarcos99

3

คุณยังสามารถใช้: f ตามด้วย: w


3
นี่จะไม่ลบไฟล์เก่า
Keith Pinson

1

สคริปต์ตัวเล็ก ๆ นี้ไม่สมบูรณ์แบบ (การรับคืนพิเศษที่คุณต้องกด) แต่มันก็เป็นงานที่ทำได้

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>

0

อีกวิธีหนึ่งคือใช้ netrw ซึ่งเป็นส่วนกำเนิดของกลุ่ม

:e path/to/whatever/folder/

จากนั้นมีตัวเลือกในการลบเปลี่ยนชื่อ ฯลฯ

ต่อไปนี้เป็นแผนผังคีย์เพื่อเปิด netrw ไปยังโฟลเดอร์ของไฟล์ที่คุณกำลังแก้ไข:

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

0

:sav newfile | !rm #

โปรดทราบว่าจะไม่ลบไฟล์เก่าออกจากรายการบัฟเฟอร์ หากสิ่งสำคัญสำหรับคุณคุณสามารถใช้สิ่งต่อไปนี้แทน:

:sav newfile | bd# | !rm #

โดยการใช้ไซต์ของเรา หมายความว่าคุณได้อ่านและทำความเข้าใจนโยบายคุกกี้และนโยบายความเป็นส่วนตัวของเราแล้ว
Licensed under cc by-sa 3.0 with attribution required.