8

* I previously asked a question but it was not the correct question. Now I made the correct question and fixed sample code. And I will up an answer which partially cites an answer to the previous question. *

I would like to default value to arrays in bash. Please see following,

function chmod_chown_func() {
  local file_path="$1"
  local chmod_options[2]=${2:='-R 744'}  # This line has error.
  local chown_options[2]=${3:='-R root:root'}  # This line has error.
  sudo chmod "${chmod_options[@]}" "${file_path}"
  sudo chown "${chown_options[@]}" "${file_path}"
}

chmod_chown_func "test.txt"

The error message is

$2: cannot assign in this way

Thank you very much.

3 Answers 3

2

Parameter Expansions

Yes, the expansion ${a:=default} changes the value of a.
It is called "Assign Default Values" in the bash manual.

$ unset a
$ echo "<${a}>  and  <${a:=default}>, But <${a}>"
<>  and  <default>, But <default>

But that syntax could not be applied to positional parameters.
Positional parameters can be (mostly) changed with set.

$ echo "$@"
a b c
$ set -- d e f
$ echo "$@"
d e f

But you can use the expansion of "Use default value" as called in the manual:

$ unset a
$ echo "<${a}>  and  <${a:-default}>, But <${a}>"
<>  and  <default>, But <>

To assign value(s) to an array variable.

A common idiom is

$ array=( aaa bbb ccc )
$ echo "${array[1]}"
bbb

Or:

$ declare -a array=( aaa bbb ccc )

Which also will make the variable local to a function if used inside the function.

However, it comes with the detail that wildcards (*, ? and []) will be expanded (unless quoted or the option set -f is used).

Overall, it is better to use read:

$ IFS=' ' read -a array <<<"$a"

Array index

You can not assign a whole array by using one index. This:

chmod_options[2]=${2:-'-R 744'}

Will only create one array value, at index 2. A better way will be:

chmod_options=( ${2:--R 744} )

Or, as explained above:

IFS=' ' read -a chmod_options <<<"${2:--R 744}"
Sign up to request clarification or add additional context in comments.

1 Comment

thank you for telling detailed and better answer about initialization of array with default values.
2

The follwings are error points and an answer code.

Error 1: The default value by ${variable:='some value'} does not work with positional parameter. It should be ${variable:-'some value'}

Error 2: To assign an default value to an array, declare an array and assign a default array value to it.

An example answer code is following

function chmod_chown_func() {
  local file_path="$1"
  local -a chmod_options=${2:-( -R 744 )}
  local -a chown_options=${3:-( -R root:root )}
  sudo chmod "${chmod_options[@]}" "${file_path}"
  sudo chown "${chown_options[@]}" "${file_path}"
}

Comments

0

I didn't have much luck with the existing answers, so might as well KISS and use a little logic to determine if the array is empty, and then assign the default value if necessary.

local -a chmod_options="$2"
local -a chown_options="$3"
# Assign default value if chmod_options is an empty string or array
[[ -z "$chmod_options" || ${#chmod_options[@]} -eq 0 ]] && chmod_options=('-R 744')
# Assign default value if chown_options is an empty string or array
[[ -z "$chown_options" || ${#chown_options[@]} -eq 0 ]] && chown_options=('root:root')

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.