วิธีแก้ไขเนื้อหาจากอินพุตมาตรฐาน


15

ฉันต้องการแก้ไขเนื้อหาในกลุ่มที่สร้างขึ้นแบบไดนามิกจากบรรทัดคำสั่งโดยไม่ต้องมีไฟล์

ในตัวอย่าง:

$ echo This is example. | vim /dev/stdin
$ cat /etc/hosts | vim /dev/stdin

แต่มันล้มเหลวด้วยข้อผิดพลาด:

เป็นกลุ่ม: คำเตือน: อินพุตไม่ได้มาจากเทอร์มินัล

เป็นกลุ่ม: ข้อผิดพลาดในการอ่านอินพุตกำลังออก ...

เป็นไปได้ไหมที่จะบรรลุเป้าหมายนั้น?


:help stdin... มันวิเศษมากที่คนเราสามารถหาคำตอบได้อย่างรวดเร็วโดยถามคำถามของพวกเขาเกี่ยวกับเอกสารในตัว
dash-tom-bang

คำตอบ:


24

คุณต้องใช้-แทนชื่อไฟล์ในบรรทัดคำสั่ง:

echo This is example. | vim -

คำสั่งดังกล่าวจะเปิดบัฟเฟอร์ที่ไม่มีชื่อที่เต็มไปด้วยข้อความที่อ่านจากอินพุตมาตรฐาน


7
การใช้-สำหรับ stdin นั้นเป็นมาตรฐานสำหรับเครื่องมือ commandline
Martin Tournoij

6

นี่เป็นเพียงส่วนใหญ่ทราบเกี่ยวกับความสนุกสนานbashและreadlineแต่ถ้าคุณตั้งค่าของEDITORตัวแปรสภาพแวดล้อมในการvimตีCtrl+ x+ จะเปิดขึ้นบรรทัดปัจจุบันในe vimนอกจากนี้หากคุณพิมพ์Meta(Alt/Opt/Esc)+ Ctrl+ eทุบตีจะทำการขยายสถานที่ในบรรทัดคำสั่งปัจจุบันคือ:

$ echo $EDITOR # Assuming EDITOR was set

ด้วยMeta(Alt/Opt/Esc)+ Ctrl+ eจะกลายเป็น

$ echo vim # Assuming EDITOR was set

ด้วยCtrl+ x+ eจะกลายเป็น

1 echo vim # Assuming EDITOR was set
~
~
/tmp/sometmpbufferfile

โปรดทราบว่าเมื่อออกเป็นกลุ่มเนื้อหาของบัฟเฟอร์กลุ่มจะถูกดำเนินการในบรรทัดคำสั่ง

คุณสมบัติเหล่านี้มีประโยชน์มากสำหรับฉันเมื่อฉันต้องการทำคำสั่งหลายบรรทัดใน bash เช่นสำหรับลูปหรือโปรแกรมที่ต้องการคำสั่งที่นี่และให้วิธีที่น่าสนใจในการบันทึกประวัติของบรรทัดคำสั่งลงในไฟล์สำหรับใช้ในภายหลัง

ดังนั้นเพื่อตอบคำถามเดิมคุณสามารถเขียนได้

$ This is an example

และจากนั้นกดCtrl+ x+ โหลดขึ้นมาในe vimนอกจากนี้คุณสามารถมี

 $ $(cat /etc/hosts)

และทำMeta(Alt/Opt/Esc)+ Ctrl+ eจากนั้นCtrl+ x+ eซึ่งจะทำให้ไฟล์โฮสต์ทั้งหมดในหนึ่งบรรทัดและโหลดขึ้นในvim(อาจไม่ใช่การใช้งานที่ดีที่สุดของคุณสมบัติเหล่านี้ - อย่างไรก็ตามประโยชน์ของวิธีการเหล่านี้สามารถคาดการณ์จากตัวอย่างที่กล่าวถึง ที่นี่)

โปรดทราบว่าฉันคิดว่าคุณreadlineถูกตั้งค่าเป็นemacsโหมด หากคุณreadlineตั้งค่าเป็นvimโหมดคุณสามารถค้นพบการเชื่อมโยงที่เกี่ยวข้องได้อย่างง่ายดายโดยใช้คำสั่ง:

bind -p

และการค้นหาedit-and-execute-commandหรือshell-expand-lineซึ่งมีความสัมพันธ์ตามลำดับผูกCtrl+ x+ eและMeta(Alt/Opt/Esc)+ +Ctrle


คุณสามารถบอก bash ให้ใช้การเชื่อมโยงปุ่ม vi แทน emacs ใช้set -o viเพื่อเปิด จากนั้นคุณสามารถใช้การvแมปในโหมดปกติเพื่อแก้ไขคำสั่งปัจจุบันในตัวแก้ไขของคุณ
Quincy Bowers

1
แน่นอนว่านี่เป็นกลอุบายที่ยอดเยี่ยมในการแก้ไขบรรทัดคำสั่งโดยใช้ vi แต่มีปัญหาอย่างน้อยสองข้อที่ใช้วิธีนี้ในการอ่านข้อความจาก stdin: 1. shell-expand-lineลบบรรทัดใหม่ออกจากข้อความที่ขยายและ 2. edit-and-execute-commandพยายามดำเนินการคำสั่งที่เขียนในบัฟเฟอร์ ไม่ว่ามันจะถูกบันทึกไว้หรือไม่ก็ตามเมื่อคุณออกจาก vi
toro2k

ว้าวมันยอดเยี่ยมมาก ฉันได้เรียนรู้สิ่งใหม่เกี่ยวกับ readline ทุกวันดูเหมือนว่า ...
Doorknob

2

ใน bash ฉันพบว่ามีประโยชน์ในการใช้การทดแทนกระบวนการโดยใช้<(command)ไวยากรณ์ตัวอย่างเช่น:

vim <(echo This is example.)
vim <(cat /etc/hosts)

ดูสิ่งนี้ด้วย:


4
หมายเหตุสิ่งนี้จะไม่ทำงานในทุกเชลล์ ฉันคิดว่ามันจะทำงานในbashและzsh(และไม่ได้sh, ksh, dash, fish, csh, tcshฯลฯ )
มาร์ติน Tournoij

@Carpetsmoker ควรทำงานใน ksh88 ขึ้นไปฉันคิดว่า แต่ใช่กระบวนการทดแทนไม่ใช่ POSIX
muru

4
และระวังอย่าหลอกตัวเอง! /proc/PID/fd/FDเมื่อคุณเริ่มเป็นกลุ่มด้วยวิธีนี้จะเปิดบัฟเฟอร์สำหรับไฟล์เช่น หากคุณเขียนบัฟเฟอร์และออกจากโปรแกรมเป็นกลุ่มจะไม่บ่น แต่ไฟล์ที่คุณเขียนจะถูกลบออกโดยระบบปฏิบัติการ การใช้-เป็นชื่อไฟล์บัฟเฟอร์ที่เปิดไม่มีไฟล์ที่เกี่ยวข้องดังนั้นหากคุณพยายามที่จะออกโดยไม่ใช้ (ตราบใดที่คุณไม่ใช้คำสั่ง bang หรือคล้ายกัน) การบันทึก Vim จะเตือนคุณ
toro2k

1
นี้เป็นสิ่งที่ดีเพราะมัน generalizes vimdiff <(echo foo) <(echo bar)ดีเพื่อ
wchargin

@ toro2k เพื่อติดตามดูเหมือนว่าใช้:nextและ:prevอ่านสตรีมอีกครั้งและไม่ได้อะไรเลย นอกจากนี้ยังมีมูลค่าการกล่าวถึงว่ากระบวนการไม่ขนานกัน - เช่นการcat <(sleep 3; echo a) <(echo b)พิมพ์ตามลำดับ - และในขณะที่catinterleaves เขียนและอ่านvimรอไฟล์ "เสร็จสิ้นการอ่าน" ก่อนที่จะแสดงทั้งหมด แต่นอกกรอบ
John P

-1

หากการใช้ไพพ์ไลน์กับ Vim ใหม่ไม่ใช่ข้อกำหนดคุณสามารถใช้ความสามารถของ Vim ในการดึงเอาท์พุทของคำสั่งลงในบัฟเฟอร์ปัจจุบันควบคู่ไปกับการมีบัฟเฟอร์สำรองที่ไม่ใช่ไฟล์ (เช่นเดียวกับ:newหรือแก้ไขไฟล์ที่ไม่มีอยู่)

:read!cat /etc/hosts ในโหมดคำสั่งจะวางผลลัพธ์ลงในบัฟเฟอร์ปัจจุบันของคุณด้านล่างตำแหน่งเคอร์เซอร์ปัจจุบัน

นอกเหนือจากการลบบรรทัดแรกที่ว่างเปล่าซึ่งยังคงอยู่เมื่อทำสิ่งนี้บนบัฟเฟอร์ที่ว่างเปล่ามันทำงานได้ดีและสะดวกมากหาก Vim ทำงานอยู่แล้ว


1
คำถามนี้จะตอบคำถามได้อย่างไร
muru

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