Re: bug adding K,V pairs to existing hash with HASH+=([K]=V)
On 2/16/16 2:06 AM, Dan Douglas wrote: > Ah so `arr+=([a]=x [b]=y)` will no longer be the same as `arr+=([a]+=x > [b]+=y)`? I never liked that for associative arrays because the only > workaround was to do multiple arr[key]= assignments to update or add > more than one element at a time. > > My thinking was that this is due to bash's unique auto-incrementing of > indexed array keys. A simple bug, nothing more. -- ``The lyf so short, the craft so long to lerne.'' - Chaucer ``Ars longa, vita brevis'' - Hippocrates Chet Ramey, ITS, CWRUc...@case.eduhttp://cnswww.cns.cwru.edu/~chet/
Re: bug adding K,V pairs to existing hash with HASH+=([K]=V)
On Mon, Feb 15, 2016 at 11:30:13PM -0800, Linda Walsh wrote: > For an array, you mean? like > array a=( 1 2 3) > array a+=( 4 5 6) > then you get array a=(5 7 9). Oh dear gods, no. imadev:~$ a=(1 2 3) imadev:~$ a+=(4 5 6) imadev:~$ declare -p a declare -a a='([0]="1" [1]="2" [2]="3" [3]="4" [4]="5" [5]="6")' If you're proposing a change to this, it will break MANY scripts.
Re: bug adding K,V pairs to existing hash with HASH+=([K]=V)
Sorry, spoofed identity (thanks gmail for picking a random sender). I'll be rid of gmail as soon as I get a little free time.
Re: bug adding K,V pairs to existing hash with HASH+=([K]=V)
\On Tue, Feb 16, 2016 at 1:30 AM, Linda Walshwrote: > > > Dan Douglas wrote: >> >> Ah so `arr+=([a]=x [b]=y)` will no longer be the same as `arr+=([a]+=x >> [b]+=y)`? I never liked that for associative arrays because the only >> workaround was to do multiple arr[key]= assignments to update or add >> more than one element at a time. >> >> My thinking was that this is due to bash's unique auto-incrementing of >> indexed array keys. Since in ksh you're not allowed to specify an >> index for one element of a compound assignment without specifying it >> for all elements, bash has some additional things to consider. >> >> ~ $ bash-4.2 -c 'typeset -ia a=({0..5}); a+=([0]+=1 {2..4}); typeset -p >> a' >> declare -ai a='([0]="1" [1]="3" [2]="5" [3]="7" [4]="4" [5]="5")' >> >> Bash 4.4: >> ~ $ ./doc/programs/bash-build/bash -c 'typeset -ia a=({0..5}); >> a+=([0]+=1 {2..4}); typeset -p a' >> declare -ai a=([0]="1" [1]="2" [2]="3" [3]="4" [4]="4" [5]="5") >> >> I almost think it makes sense to treat ordered and unordered >> collections differently. > > Why? >> >> With an unordered collection an outer += >> should obviously mean "add or update for each assignment". > > For an array, you mean? like > array a=( 1 2 3) > array a+=( 4 5 6) > then you get array a=(5 7 9). Or are you saying > for an ordered array you'd have to use indexes, like > array a=(1 2 3) > array a+=([0]=4 [1]=7 [2]=10), then that would do your > -- but wouldn't that be doing a vector operation of > sorts? I mean exactly the example I posted. In bash if you explicitly specify an index for an assignment at any point within an auto-incrementing compound assignment, bash will jump to that position and continue incrementing. Bash is the only shell that has that property. There's nothing wrong with that feature but the question of what to do when an auto-incrementing assignment encounters an element with a previous value isn't as obvious because the semantics differ. For an ordered collection the outer += translates to "append to the list" while with an unordered collection it roughly means to "union" the two sets of keys. You could argue that for consistency bash should always bulldoze over previous values even if auto-incrementing keys. That makes sense from a certain perspective and is consistent. From another perspective you might expect the outer += to mean append for each sub-assignment to an auto-incrementing array when not appending to the end of the array. That especially makes sense if it's an integer array. I can understand the logic either way. I wrote about all of these issues years ago (I'm pretty sure also on this list) so people probably know about them and possibly believed the old behavior was by design like I did. http://wiki.bash-hackers.org/syntax/arrays#bugs_and_portability_considerations.
Re: bug adding K,V pairs to existing hash with HASH+=([K]=V)
Dan Douglas wrote: Ah so `arr+=([a]=x [b]=y)` will no longer be the same as `arr+=([a]+=x [b]+=y)`? I never liked that for associative arrays because the only workaround was to do multiple arr[key]= assignments to update or add more than one element at a time. My thinking was that this is due to bash's unique auto-incrementing of indexed array keys. Since in ksh you're not allowed to specify an index for one element of a compound assignment without specifying it for all elements, bash has some additional things to consider. ~ $ bash-4.2 -c 'typeset -ia a=({0..5}); a+=([0]+=1 {2..4}); typeset -p a' declare -ai a='([0]="1" [1]="3" [2]="5" [3]="7" [4]="4" [5]="5")' Bash 4.4: ~ $ ./doc/programs/bash-build/bash -c 'typeset -ia a=({0..5}); a+=([0]+=1 {2..4}); typeset -p a' declare -ai a=([0]="1" [1]="2" [2]="3" [3]="4" [4]="4" [5]="5") I almost think it makes sense to treat ordered and unordered collections differently. Why? With an unordered collection an outer += should obviously mean "add or update for each assignment". For an array, you mean? like array a=( 1 2 3) array a+=( 4 5 6) then you get array a=(5 7 9). Or are you saying for an ordered array you'd have to use indexes, like array a=(1 2 3) array a+=([0]=4 [1]=7 [2]=10), then that would do your -- but wouldn't that be doing a vector operation of sorts? ^^ You can make similar "logic" jumps in going the same way in arrays as you can hashes. ... To me, if you want to add elements to an array or hash and use '=' on the interior, that should assign, like scalars do. Use '+=' on the interior to get an increment of the scalar. Why would you assign special non-uniform rules for scalars in an array vs. ones not in an array?
Re: bug adding K,V pairs to existing hash with HASH+=([K]=V)
Ah so `arr+=([a]=x [b]=y)` will no longer be the same as `arr+=([a]+=x [b]+=y)`? I never liked that for associative arrays because the only workaround was to do multiple arr[key]= assignments to update or add more than one element at a time. My thinking was that this is due to bash's unique auto-incrementing of indexed array keys. Since in ksh you're not allowed to specify an index for one element of a compound assignment without specifying it for all elements, bash has some additional things to consider. ~ $ bash-4.2 -c 'typeset -ia a=({0..5}); a+=([0]+=1 {2..4}); typeset -p a' declare -ai a='([0]="1" [1]="3" [2]="5" [3]="7" [4]="4" [5]="5")' Bash 4.4: ~ $ ./doc/programs/bash-build/bash -c 'typeset -ia a=({0..5}); a+=([0]+=1 {2..4}); typeset -p a' declare -ai a=([0]="1" [1]="2" [2]="3" [3]="4" [4]="4" [5]="5") I almost think it makes sense to treat ordered and unordered collections differently. With an unordered collection an outer += should obviously mean "add or update for each assignment". For an ordered collection when appending beginning at an index lower than the max index I'm not so sure. -- Dan Douglas
Re: bug adding K,V pairs to existing hash with HASH+=([K]=V)
On 2/15/16 3:48 PM, Linda Walsh wrote: > > > Chet Ramey wrote: >> On 2/15/16 12:35 PM, Linda Walsh wrote: >> >> >>> Bash Version: 4.3 >>> Patch Level: 42 >>> Release Status: release >>> >>> Description: >>> [Detailed description of the problem, suggestion, or complaint.] >>> >>> When I create hash and later add keys using the form >>> "HASH+=([key]=VALUE)", if KEY already existed in the HASH, then >>> I get the += applied to the VALUE as well >>> (strings get appended, ints get added). >>> >>> Whether '+=' or '=' is used in the VALUE assignment, the >>> effect is '+='. >>> >> >> http://lists.gnu.org/archive/html/bug-bash/2014-11/msg00169.html >> http://lists.gnu.org/archive/html/bug-bash/2014-11/msg00179.html >> > > Right... and? > > Did it never make it in to 4.3? It will be in bash-4.4. -- ``The lyf so short, the craft so long to lerne.'' - Chaucer ``Ars longa, vita brevis'' - Hippocrates Chet Ramey, ITS, CWRUc...@case.eduhttp://cnswww.cns.cwru.edu/~chet/
Re: bug adding K,V pairs to existing hash with HASH+=([K]=V)
Chet Ramey wrote: On 2/15/16 12:35 PM, Linda Walsh wrote: Bash Version: 4.3 Patch Level: 42 Release Status: release Description: [Detailed description of the problem, suggestion, or complaint.] When I create hash and later add keys using the form "HASH+=([key]=VALUE)", if KEY already existed in the HASH, then I get the += applied to the VALUE as well (strings get appended, ints get added). Whether '+=' or '=' is used in the VALUE assignment, the effect is '+='. http://lists.gnu.org/archive/html/bug-bash/2014-11/msg00169.html http://lists.gnu.org/archive/html/bug-bash/2014-11/msg00179.html Right... and? Did it never make it in to 4.3? (Note, the "auto generated info included with this bug report was wrong -- as explained in next bug report...)
Re: bug adding K,V pairs to existing hash with HASH+=([K]=V)
On 2/15/16 12:35 PM, Linda Walsh wrote: > Bash Version: 4.2 > Patch Level: 53 > Release Status: release > > Description: > [Detailed description of the problem, suggestion, or complaint.] > > When I create hash and later add keys using the form > "HASH+=([key]=VALUE)", if KEY already existed in the HASH, then > I get the += applied to the VALUE as well > (strings get appended, ints get added). > > Whether '+=' or '=' is used in the VALUE assignment, the > effect is '+='. http://lists.gnu.org/archive/html/bug-bash/2014-11/msg00169.html http://lists.gnu.org/archive/html/bug-bash/2014-11/msg00179.html -- ``The lyf so short, the craft so long to lerne.'' - Chaucer ``Ars longa, vita brevis'' - Hippocrates Chet Ramey, ITS, CWRUc...@case.eduhttp://cnswww.cns.cwru.edu/~chet/
bug adding K,V pairs to existing hash with HASH+=([K]=V)
Configuration Information [Automatically generated, do not change]: Machine: x86_64 OS: linux-gnu Compiler: gcc -I/home/abuild/rpmbuild/BUILD/bash-4.2 -L/home/abuild/rpmbuild/BUILD/bash-4.2/../readline-6.2 Compilation CFLAGS: -DPROGRAM='bash' -DCONF_HOSTTYPE='x86_64' -DCONF_OSTYPE='linux-gnu' -DCONF_MACHTYPE='x86_64-suse-linux-gnu' -DCONF_VENDOR='suse' -DLOCALEDIR='/usr/share/locale' -DPACKAGE='bash' -DSHELL -DHAVE_CONFIG_H -I. -I. -I./include -I./lib -fmessage-length=0 -grecord-gcc-switches -O2 -Wall -D_FORTIFY_SOURCE=2 -fstack-protector -funwind-tables -fasynchronous-unwind-tables -g -D_GNU_SOURCE -DRECYCLES_PIDS -Wall -g -Wuninitialized -Wextra -Wno-unprototyped-calls -Wno-switch-enum -Wno-unused-variable -Wno-unused-parameter -ftree-loop-linear -pipe -DBNC382214=0 -DIMPORT_FUNCTIONS_DEF=0 -fprofile-use uname output: Linux Ishtar 4.1.0-Isht-Van #2 SMP PREEMPT Tue Jun 23 07:52:09 PDT 2015 x86_64 x86_64 x86_64 GNU/Linux Machine Type: x86_64-suse-linux-gnu Bash Version: 4.2 Patch Level: 53 Release Status: release Description: [Detailed description of the problem, suggestion, or complaint.] When I create hash and later add keys using the form "HASH+=([key]=VALUE)", if KEY already existed in the HASH, then I get the += applied to the VALUE as well (strings get appended, ints get added). Whether '+=' or '=' is used in the VALUE assignment, the effect is '+='. Can I suggest that, maybe, this "interesting" behavior be limited to the in-parens, "[KEY][+]=VAL" part? Repeat-By: (Example) > alias sv='my -p' #(show_var) > hash cfg=(); sv cfg declare -A cfg='()' #empty hash > cfg+=([one]=1 [two]=2) ; sv cfg declare -A cfg='([one]="1" [two]="2" )' #two elements > cfg+=([two]=2 [three]=3) ; sv cfg declare -A cfg='([one]="1" [two]="22" [three]="3" )' #Note key 'two' > int cfg # switch existing hash to integers. # explicitly use += in some > cfg+=([one]+=1 [two]=2 [three]+=0-3 )# VALUE assignments > sv cfg declare -Ai cfg='([one]="2" [two]="24" [three]="0" )' Fix: Honor "=" to mean "set" and allow "+=" to continue to access this behavior.