Vimでカーソルより前の数字をインクリメントする

1 min読了の目安(約800字TECH技術記事

ノーマルモードの<C-a>, <C-x>でカーソル以降の最初の数字を増減させられる。
('nrformats'オプションによっては数字でない場合もある)

この機能はカーソル以降にインクリメント対象がなければ何も起きない。
これをカーソル以前に対しても動くようにしたら少し便利になった。

以下で1 1 hoge|から<C-a>して1 2| hogeにできる。
(|をカーソル位置とする)

function! s:inc_or_dec(is_inc) abort
    let key = a:is_inc ? "\<C-a>" : "\<C-x>"
    let line = getline('.')
    let col = col('.')
    let pattern = '\v\d+\ze[^[:digit:]]*$'
    if matchend(line[col - 1:], pattern) == -1
        let idx = matchend(line[:col - 1], pattern)
        if idx != -1
            return printf('%dh%s', col - idx, key)
        endif
    endif
    return key
endfunction

nnoremap <expr> <C-a> <SID>inc_or_dec(v:true)
nnoremap <expr> <C-x> <SID>inc_or_dec(v:false)

カーソル以降を探して、なければカーソル以前を探す。
カーソル以前にあればマッチの末尾までカーソルを戻してインクリメントする実装。

'nrformats'alphaを含む場合は考慮していない。