Vâng, có một chức năng thực hiện chỉ một lần trên một phạm vi, nối thêm từ khóa range
. Ví dụ.
fun Foo() range
...
endfun
Sau đó, chức năng của bạn có thể tự quản lý phạm vi bằng các thông số đặc biệt a: firstline và: lastline. (Xem :help a:firstline
để biết chi tiết.)
Tuy nhiên tôi nghĩ rằng trong trường hợp này yêu cầu của bạn chỉ đơn giản là đủ để được hoàn thành với một lớp lót sử dụng :global
.
Chúng tôi có thể thực hiện với các đầu vào và đầu ra được chỉ định tốt hơn. Nhưng giả sử một tập tin chứa
Item a: <total>
Subitem: 10 min
Subitem 2: 20 min
Item b: <total>
Subitem: 10 min
Subitem 2: 23 min
Item c: <total>
Subitem: 10 min
Subitem 2: 23 min
Subitem 3: 43 min
và một chức năng được xác định như
fun! Sum(n)
let g:s += a:n
return a:n
endfun
thì đây sẽ tổng hợp các subitems (tất cả cùng một dòng)
:g/^Item/ let g:s = 0 | mark a | +,-/\nItem\|\%$/ s/\v(\d+)\ze\s+min$/\=Sum(submatch(0))/g | 'a s/<total>/\=(g:s . ' min')/
và sản xuất sản lượng này
Item a: 30 min
Subitem: 10 min
Subitem 2: 20 min
Item b: 33 min
Subitem: 10 min
Subitem 2: 23 min
Item c: 76 min
Subitem: 10 min
Subitem 2: 23 min
Subitem 3: 43 min
Nhân tiện, lệnh trên hoạt động trên toàn bộ bộ đệm. Nếu bạn đánh dấu một dãy đầu tiên và sau đó nhấn phím :
, vim sẽ tự động thêm lệnh của bạn với '<,'>
có nghĩa là lệnh sau sẽ hoạt động từ đầu đến cuối phạm vi được đánh dấu.
Ví dụ: làm nổi bật các dòng 1 đến 5 và sau đó chạy lệnh (:'<,'> g/...
) tạo ra kết quả này
Item a: 30 min
Subitem: 10 min
Subitem 2: 20 min
Item b: 33 min
Subitem: 10 min
Subitem 2: 23 min
Item c: <total>
Subitem: 10 min
Subitem 2: 23 min
Subitem 3: 43 min
Một lưu ý cuối cùng. Nếu một trong các nhóm không có phụ đề, ví dụ:
Item a: <total>
Subitem: 10 min
Subitem 2: 20 min
Item b: <total>
Item c: <total>
Subitem: 10 min
Subitem 2: 23 min
Subitem 3: 43 min
sau đó lệnh sẽ hủy bỏ lỗi 'Phạm vi không hợp lệ' khi nó đến mục thứ hai. Bạn có thể yêu cầu Vim bỏ qua điều này và tiếp tục bất kể bằng cách thêm tiền tố cho toàn bộ lệnh với :silent!
.
EDIT
Chỉ cần một lời giải thích nhanh chóng của công việc của tôi và tại sao lâu một lót.
- Tôi thích
:g
và các lệnh cũ.
- Tôi đã xây dựng lệnh tương tác bằng cách sử dụng lịch sử dòng lệnh và cửa sổ dòng lệnh để chỉnh sửa.
- Khi hoàn thành, tôi dán các lệnh một lần như thế này vào bộ đệm: Tôi có ánh xạ để thực thi dòng hiện tại như một lệnh cũ. Bằng cách đó, lệnh luôn luôn có sẵn khi tôi cần nó. Để sử dụng thường xuyên hơn, bạn có thể muốn có một lệnh, hàm hoặc một ftplugin.
nó ... đẹp ... Nghiêm túc, cảm ơn cho tốt nhất câu trả lời SO Tôi đã có thể bao giờ nhận được. –
Btw, đối với bất kỳ ai nghĩ rằng lệnh g: ở trên trông phức tạp, nó không thực sự. Cú pháp là rất ngắn gọn mà có thể cung cấp cho nó sự xuất hiện, nhưng các hoạt động thực sự khá đơn giản; không có bất kỳ thủ đoạn thông minh nào. Chỉ cần tra cứu các bit bạn không nhận được trong tài liệu tuyệt vời, hoặc hỏi về SO hoặc nhóm vim_use Google. – 1983
Nó đã cho tôi một thời gian dài để hiểu ... vì vậy đây là một lời giải thích: : g bắt đầu một lệnh toàn cầu /^ Item/Lệnh chạy ở mỗi dòng phù hợp với^mục let g: s = 0 đánh dấu Lưu vị trí của con trỏ trong một số +, -/\ nMục \ | \% $/s/\ v (\ d +) \ ze \ s + phút $/\ = Tổng (số phụ (0))/g Đây là một con quái vật khổng lồ của một lệnh thay thế. Phần cho đến 'đầu tiên' là phạm vi, phần giữa 's' và '$' là mẫu và hàm gọi là thay thế (không có gì thực sự được thay thế) 'a quay lại vị trí được đánh dấu là s//\ = (g: s. 'min')/ cuối cùng thay thế –