Re: ${parameter/pattern/string} behaviour changed
d...@ftb-esv.de wrote: Description: Command: x="a b c"; echo "'${x// /','}'" On old systems the output is: 'a','b','c' In this version the output is: 'a,b,c' This new behavior breaks some scripts. --- The way I'd see it is that the ',' in the replacement text field needs to have its quotes quoted. I.e. this works: echo "'${x// /"','"}'" 'a','b','c' So it's really just a matter of quote removal occurring in the replacement text. In that respect, it is consistent with: echo "$(echo 'hi')" hi where you get hi w/no quotes, vs.: echo "$(echo "'hi'")" 'hi' If quotes didn't function in the 2nd part, I'd think it a bug, since it would be using the literal value in the 2nd part and one wouldn't be able to use a variable (like Greg did, though I didn't see the need to put the quotes in a variable).
Re: ${parameter/pattern/string} behaviour changed
On Fri, Mar 16, 2018 at 1:18 PM, wrote: [...] > Bash Version: 4.3 > Patch Level: 42 > Release Status: release > > Description: > Command: x="a b c"; echo "'${x// /','}'" > On old systems the output is: 'a','b','c' > In this version the output is: 'a,b,c' > This new behavior breaks some scripts. Hm, 4.3 is almost 4 years old, so that's hardly "new" behavior. Furthermore, this behavior changed as a result of a bug report, see: - http://lists.gnu.org/archive/html/bug-bash/2012-02/msg00106.html - http://lists.gnu.org/archive/html/bug-bash/2013-03/msg00100.html
Re: ${parameter/pattern/string} behaviour changed
On Fri, Mar 16, 2018 at 08:18:53PM +0100, d...@ftb-esv.de wrote: > Command: x="a b c"; echo "'${x// /','}'" > On old systems the output is: 'a','b','c' > In this version the output is: 'a,b,c' So, this LOOKS like an attempt to take a list, and write it out with single quotes around each element, and commas BETWEEN the quoted elements (but no trailing or leading comma). Obviously this is not the best way to store a list, nor is it the best way to write a list to stdout with those modifications. If you want to continue along these cheap hack lines, then you need to store the quote character in a variable, and use that inside the parameter expansion. Thus: wooledg:~$ string="a b c"; q=\'; echo "'${string// /$q,$q}'" 'a','b','c' But this is really not the way I would approach the problem. Granted, bash is not a great language for operating on lists, but still Printing a list, with modifications, WITH an extra trailing comma, is trivial: wooledg:~$ list=(a b c); printf "'%s'," "${list[@]}"; echo 'a','b','c', Given this, probably the *easiest* way to get the desired result without the extra trailing comma would be to remove it afterward: wooledg:~$ list=(a b c); printf -v tmp "'%s'," "${list[@]}"; echo "${tmp%,}" 'a','b','c' I would probably go with that, if I had to do this in bash.
${parameter/pattern/string} behaviour changed
Configuration Information [Automatically generated, do not change]: Machine: x86_64 OS: linux-gnu Compiler: gcc -I/home/abuild/rpmbuild/BUILD/bash-4.3 -L/home/abuild/rpmbuild/BUILD/bash-4.3/../readline-6.3 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 -Wno-parentheses -ftree-loop-linear -pipe -DBNC382214=0 -DIMPORT_FUNCTIONS_DEF=0 -fprofile-use uname output: Linux hetz6 4.4.74-18.20-default #1 SMP Fri Jun 30 19:01:19 UTC 2017 (b5079b8) x86_64 x86_64 x86_64 GNU/Linux Machine Type: x86_64-suse-linux-gnu Bash Version: 4.3 Patch Level: 42 Release Status: release Description: Command: x="a b c"; echo "'${x// /','}'" On old systems the output is: 'a','b','c' In this version the output is: 'a,b,c' This new behavior breaks some scripts.
Re: String behaviour
On Fri, Jun 24, 2011 at 10:38, BX wrote: > #/bin/bash > # file1 > import() > { > source file2 > } > > import > > echo v1=$v1, v2=$v2, v3=$v3 > > #/bin/bash > # file2 > v1=v1 > declare -x v2=v2 > declare v3=v3 > > Run above script by > $ bash file1 > > Expected result: v1=v1, v2=v2, v3=v3 > Real result: v1=v1, v2=, v3= >From the documentation here: info '(bash)Shell Functions' we have: When the name of a shell function is used as a simple command name, the list of commands associated with that function name is executed. Shell functions are executed in the current shell context; no new process is created to interpret them. ... The BODY of the function is the compound command COMPOUND-COMMAND and from: info '(bash)Command Grouping' we have: Placing a list of commands between curly braces causes the list to be executed in the current shell context. No subshell is created. and from: info '(bash)Bourne Shell Builtins' we know that the `source' builtin works as follows: Read and execute commands from the FILENAME argument in the current shell context and from: info '(bash)Bash Builtins' we have When used in a function, `declare' makes each NAME local, as with the `local' command, unless the `-g' option is used. So, basically, the results are as expected: You execute the function `import', which executes `source file2' in the current shell context, which creates the variable `v1' in the current shell context, but creates the variables `v2' and `v3' local to the function being executed in the current shell context, so that by the echo statement, only `v1' is defined. Sincerely, Michael Witten