commit 7f8c1e53a6c27ce6957b102d7b1c9ec808f61d60
parent c690f1019477e4c9a63e22e7c68bf1f65cc69fc7
Author: Sean Dewar <seandewar@users.noreply.github.com>
Date: Sat, 11 Sep 2021 19:44:11 +0100
vim-patch:8.2.2948: substitute() accepts a number but not a float expression
Problem: Substitute() accepts a number but not a float expression.
Solution: Also accept a float. (closes vim/vim#8331)
https://github.com/vim/vim/commit/7a2217bedd223df4c8bbebe731bf0b5fe8532533
Vim9script is N/A. No need to port the strict argument and
tv_get_string_buf_chk_strict(), as it's only used for Vim9script.
Like the patch, use vim_snprintf over snprintf, as the "%g" specifier in
snprintf removes the ".0" from integer floats.
This means similiar to numbers, floats are (mostly) convertable to
strings.
Co-authored-by: Bram Moolenaar <Bram@vim.org>
Diffstat:
2 files changed, 12 insertions(+), 4 deletions(-)
diff --git a/src/nvim/eval/typval.c b/src/nvim/eval/typval.c
@@ -3876,7 +3876,6 @@ static const char *const str_errors[] = {
[VAR_FUNC]= N_(FUNC_ERROR),
[VAR_LIST]= N_("E730: Using a List as a String"),
[VAR_DICT]= N_("E731: Using a Dictionary as a String"),
- [VAR_FLOAT]= e_using_float_as_string,
[VAR_BLOB]= N_("E976: Using a Blob as a String"),
[VAR_UNKNOWN]= e_using_invalid_value_as_string,
};
@@ -3899,12 +3898,12 @@ bool tv_check_str(const typval_T *const tv)
case VAR_BOOL:
case VAR_SPECIAL:
case VAR_STRING:
+ case VAR_FLOAT:
return true;
case VAR_PARTIAL:
case VAR_FUNC:
case VAR_LIST:
case VAR_DICT:
- case VAR_FLOAT:
case VAR_BLOB:
case VAR_UNKNOWN:
emsg(_(str_errors[tv->v_type]));
@@ -4275,6 +4274,9 @@ const char *tv_get_string_buf_chk(const typval_T *const tv, char *const buf)
case VAR_NUMBER:
snprintf(buf, NUMBUFLEN, "%" PRIdVARNUMBER, tv->vval.v_number); // -V576
return buf;
+ case VAR_FLOAT:
+ vim_snprintf(buf, NUMBUFLEN, "%g", tv->vval.v_float);
+ return buf;
case VAR_STRING:
if (tv->vval.v_string != NULL) {
return tv->vval.v_string;
@@ -4290,7 +4292,6 @@ const char *tv_get_string_buf_chk(const typval_T *const tv, char *const buf)
case VAR_FUNC:
case VAR_LIST:
case VAR_DICT:
- case VAR_FLOAT:
case VAR_BLOB:
case VAR_UNKNOWN:
emsg(_(str_errors[tv->v_type]));
diff --git a/test/old/testdir/test_substitute.vim b/test/old/testdir/test_substitute.vim
@@ -457,7 +457,14 @@ func Test_substitute_partial()
" 20 arguments plus one is too many
let Replacer = function('SubReplacer20', repeat(['foo'], 20))
- call assert_fails("call substitute('123', '2', Replacer, 'g')", 'E118')
+ call assert_fails("call substitute('123', '2', Replacer, 'g')", 'E118:')
+endfunc
+
+func Test_substitute_float()
+ CheckFeature float
+
+ call assert_equal('number 1.23', substitute('number ', '$', { -> 1.23 }, ''))
+ " vim9 assert_equal('number 1.23', substitute('number ', '$', () => 1.23, ''))
endfunc
" Tests for *sub-replace-special* and *sub-replace-expression* on :substitute.