BASH-Adding array element: Naming issue using array[${#array[*]}]=5
I am writing a bash script and according to interwebs, when trying to add an element to an array, the syntax is as follows:
array[${#array[*]}]=5 In my case, the array name changes depending on which loop iteration we are on... and I use variable affCtr as my counter to determine which array I will be appending to. So it should technically look something like this: core${affCtr}[${#core${affCtr}[*]}]=$tempID The problem is highlighted-- when I introduce that additional '$' since I want to use a variable there, I somehow lose the meaning of what the '*' should be. Do you guys have any idea on what might work? I've tried various combinations of parentheses, back ticks, etc. and nothing seems to work... Thanks in advance for any help! |
Hi calvarado777!
Maybe this will help. Code:
#! /bin/bash |
Actually the issue being faced is that you cannot use a variable name as the array name. You could potentially use eval but for many reasons I try to avoid it like the plague if possible.
So looking at your problem I would suggest using a case statement based on your variable 'affCtr' and then append to the appropriate array as required. |
What grail said.
An array is really just a buffed up variable and has the same general limitations in naming and setting: How can I use variable variables (indirect variables, pointers, references) or associative arrays? http://mywiki.wooledge.org/BashFAQ/006 What you're apparently wanting to do is create a multi-dimensional array, which isn't available in bash. But you can generally simulate one with an associative array and a two-part index string. Code:
declare -A myarray There's a (usually) minor problem in that associative array indexes don't sort naturally, but that can usually be overcome if necessary. If you explain your ultimate purpose in more detail then we can probably give you more explicit advice. PS: Please use ***[code][/code]*** tags around your code and data, to preserve the original formatting and to improve readability. Do not use quote tags, bolding, colors, "start/end" lines, or other creative techniques. Thanks. |
Using case statements would add complexity and using other tricks besides eval for indirect addressing could sometimes lead to unexpected reinterpretation of data like losing other lines after one. At least the complexity of it is more dangerous or evil compared to eval and one would wonder why people would go for the trouble just for the sake of keeping their pride with declaring eval as evil. So simply use eval:
Code:
eval "core${affCtr}[\${#core${affCtr}[*]}]=\$tempID" Code:
echo "core${affCtr}[\${#core${affCtr}[*]}]=\$tempID" |
No pride here ... once bitten twice shy ... after having an rm take out a third of a system before I was able to control out of it was enough for me. So my general rule of thumb is why invite the danger if a safer and easier way exists.
I do agree that in this case there will hope fully be no unwarranted issues. |
Using eval cannot "sometimes lead to unexpected reinterpretation of data" as well? Huh?
But as I've explained before, I don't consider eval to be "evil", just dangerous, non-transparent, and tricky for inexperienced people to use safely, and that it shouldn't be recommended as a solution except when absolutely necessary. I also believe that modern shells have enough features in place to make its use increasingly unnecessary. Too many people seem too eager to pull it out at every opportunity, the proverbial sledgehammer approach to scripting. (Ok, so maybe I do sometimes go too far in the other direction, but better safe than sorry.) I also think that indirect variable creation has many similar transparency and complexity (and even security) problems, and should be avoided too when possible. For example, you have to ensure that the sub-variables you're using to create the final variable name (e.g. $affCtr) only contains valid name characters in it. If you do decide indirect referencing is the way to go, then at least bash does provide several other ways to create them besides eval (read, declare and printf, as addressed in my previous link), which at the least don't require as much effort to sanitize (syntax escaping, etc) before using. Then, even if you get them set safely, correctly referencing them later can still be a job in itself. I agree that if and when bash gets -n indirect referencing it will be easier and safer, but for now, associative arrays and even things like parsing with case statements are to my mind much safer and more transparent than anything you can do with eval or referencing. |
Quote:
Quote:
Quote:
Quote:
Quote:
Quote:
Quote:
Quote:
And associative arrays on the other hand look dirty workarounds in which values which should have been placed on single variables are now indexed through hashes in one associative variable like a group. |
If you're still interested, here's a "eval"ed sample script:
Code:
$ cat example Oh. note the use of single quotes the the eval argument to suppress inappropriate parsing. </edit> |
All times are GMT -5. The time now is 11:33 PM. |