Patch 8.2.3423
Problem:    Vim9: list += list creates a new list in :def function.
Solution:   Append to the existing list.
Files:      src/structs.h, src/vim9compile.c, src/vim9execute.c,
            src/testdir/test_vim9_assign.vim


*** ../vim-8.2.3422/src/structs.h       2021-08-07 12:44:37.836256707 +0200
--- src/structs.h       2021-09-09 22:42:52.720026194 +0200
***************
*** 4106,4111 ****
--- 4106,4114 ----
      EXPR_MULT,                // *
      EXPR_DIV,         // /
      EXPR_REM,         // %
+     // used with ISN_ADDLIST
+     EXPR_COPY,                // create new list
+     EXPR_APPEND,      // append to first list
  } exprtype_T;
  
  /*
*** ../vim-8.2.3422/src/vim9compile.c   2021-08-25 22:37:33.103295301 +0200
--- src/vim9compile.c   2021-09-09 22:52:56.047211318 +0200
***************
*** 690,701 ****
      return OK;
  }
  
      static int
  generate_add_instr(
        cctx_T *cctx,
        vartype_T vartype,
        type_T *type1,
!       type_T *type2)
  {
      garray_T  *stack = &cctx->ctx_type_stack;
      isn_T     *isn = generate_instr_drop(cctx,
--- 690,705 ----
      return OK;
  }
  
+ /*
+  * Generate instruction for "+".  For a list this creates a new list.
+  */
      static int
  generate_add_instr(
        cctx_T *cctx,
        vartype_T vartype,
        type_T *type1,
!       type_T *type2,
!       exprtype_T expr_type)
  {
      garray_T  *stack = &cctx->ctx_type_stack;
      isn_T     *isn = generate_instr_drop(cctx,
***************
*** 715,721 ****
        return FAIL;
  
      if (isn != NULL)
!       isn->isn_arg.op.op_type = EXPR_ADD;
  
      // When concatenating two lists with different member types the member 
type
      // becomes "any".
--- 719,730 ----
        return FAIL;
  
      if (isn != NULL)
!     {
!       if (isn->isn_type == ISN_ADDLIST)
!           isn->isn_arg.op.op_type = expr_type;
!       else
!           isn->isn_arg.op.op_type = EXPR_ADD;
!     }
  
      // When concatenating two lists with different member types the member 
type
      // becomes "any".
***************
*** 769,775 ****
      switch (*op)
      {
        case '+':
!                 if (generate_add_instr(cctx, vartype, type1, type2) == FAIL)
                      return FAIL;
                  break;
  
--- 778,785 ----
      switch (*op)
      {
        case '+':
!                 if (generate_add_instr(cctx, vartype, type1, type2,
!                                                           EXPR_COPY) == FAIL)
                      return FAIL;
                  break;
  
***************
*** 7186,7192 ****
            {
                if (generate_add_instr(cctx,
                            operator_type(lhs.lhs_member_type, stacktype),
!                                      lhs.lhs_member_type, stacktype) == FAIL)
                    goto theend;
            }
            else if (generate_two_op(cctx, op) == FAIL)
--- 7196,7203 ----
            {
                if (generate_add_instr(cctx,
                            operator_type(lhs.lhs_member_type, stacktype),
!                                      lhs.lhs_member_type, stacktype,
!                                                         EXPR_APPEND) == FAIL)
                    goto theend;
            }
            else if (generate_two_op(cctx, op) == FAIL)
*** ../vim-8.2.3422/src/vim9execute.c   2021-09-02 18:49:02.744932328 +0200
--- src/vim9execute.c   2021-09-09 22:57:56.118792898 +0200
***************
*** 3677,3683 ****
  
                    // add two lists or blobs
                    if (iptr->isn_type == ISN_ADDLIST)
!                       eval_addlist(tv1, tv2);
                    else
                        eval_addblob(tv1, tv2);
                    clear_tv(tv2);
--- 3677,3690 ----
  
                    // add two lists or blobs
                    if (iptr->isn_type == ISN_ADDLIST)
!                   {
!                       if (iptr->isn_arg.op.op_type == EXPR_APPEND
!                                                  && tv1->vval.v_list != NULL)
!                           list_extend(tv1->vval.v_list, tv2->vval.v_list,
!                                                                        NULL);
!                       else
!                           eval_addlist(tv1, tv2);
!                   }
                    else
                        eval_addblob(tv1, tv2);
                    clear_tv(tv2);
*** ../vim-8.2.3422/src/testdir/test_vim9_assign.vim    2021-08-23 
22:22:41.158911317 +0200
--- src/testdir/test_vim9_assign.vim    2021-09-09 22:59:49.082634220 +0200
***************
*** 557,576 ****
  
  def Test_extend_list()
    var lines =<< trim END
!       vim9script
!       var l: list<number>
!       l += [123]
!       assert_equal([123], l)
    END
!   CheckScriptSuccess(lines)
  
    lines =<< trim END
-       vim9script
        var list: list<string>
        extend(list, ['x'])
        assert_equal(['x'], list)
    END
!   CheckScriptSuccess(lines)
  
    # appending to NULL list from a function
    lines =<< trim END
--- 557,577 ----
  
  def Test_extend_list()
    var lines =<< trim END
!       var l1: list<number>
!       var l2 = l1
!       assert_true(l1 is l2)
!       l1 += [123]
!       assert_equal([123], l1)
!       assert_true(l1 is l2)
    END
!   CheckDefAndScriptSuccess(lines)
  
    lines =<< trim END
        var list: list<string>
        extend(list, ['x'])
        assert_equal(['x'], list)
    END
!   CheckDefAndScriptSuccess(lines)
  
    # appending to NULL list from a function
    lines =<< trim END
*** ../vim-8.2.3422/src/version.c       2021-09-09 22:30:48.128865561 +0200
--- src/version.c       2021-09-09 22:43:54.959944831 +0200
***************
*** 757,758 ****
--- 757,760 ----
  {   /* Add new patch number below this line */
+ /**/
+     3423,
  /**/

-- 
When a fly lands on the ceiling, does it do a half roll or
a half loop?

 /// Bram Moolenaar -- [email protected] -- http://www.Moolenaar.net   \\\
///                                                                      \\\
\\\        sponsor Vim, vote for features -- http://www.Vim.org/sponsor/ ///
 \\\            help me help AIDS victims -- http://ICCF-Holland.org    ///

-- 
-- 
You received this message from the "vim_dev" maillist.
Do not top-post! Type your reply below the text you are replying to.
For more information, visit http://www.vim.org/maillist.php

--- 
You received this message because you are subscribed to the Google Groups 
"vim_dev" group.
To unsubscribe from this group and stop receiving emails from it, send an email 
to [email protected].
To view this discussion on the web visit 
https://groups.google.com/d/msgid/vim_dev/202109092101.189L1be7154407%40masaka.moolenaar.net.

Raspunde prin e-mail lui