A problem with the set syntax has been nagging me for a long time. Set
allows you to assign and erase slices of arrays using a convenient
syntax like:

set foo[1 3 7] foo bar baz

in order to assign to the first, third and seventh element of the
array foo, and with the same logic you can also use 'set -e foo[ 2 4]'
to erase the second and fourth element of foo. This seems like it's
all very clever, but unfortunatly it's actually a bit useless. The
problem is that one rarely specifys the slicing indexes literally like
that. What you'd want to do is something like

set foo[(seq 3 5)] foo bar baz

or

set idx 1 3 7
set -e foo[$idx]

but neither will work. Parameter expansion will make sure that the
former example gets expanded into

set foo[3] foo[4] foo[5] foo bar baz

Which 'set' wont understand - it only looks at the first argument to
find the variable indices to assign to, and will complain that you can
assign 5 values to a single sliceing index. Doh.

It might seem at first that in order to fix this problem, one would
have to somehow tell set what values are variable slices and what
values are values to assign. Afterall, how would one for example
otherwise assign the value 'foo[3]' to the variable foo at index 5?

Actually, it turns out that by parsing one argument at a time and
stopping whenever the number of specified indexes equals the number of
remaining arguments, one can correctly parse all such assignments with
no fear of ambiguity.

There are still a few gotchas left, though:

* Some people might expect e.g. 'set foo[1 (seq 4 6)] a b c d' to work
and use the slice indexes '1 4 5 6', but it won't, since it will
result in the slice indexes '1 4 1 5 1 6'. This is the right thing in
my opinion, but it is a bit confusing at first.
* There are situations where an incorrect slicing operation will still
result in the same number of indexes and values, resulting in silent
bugs. I belive this is is much less common than you'd think, since one
can easily check that all variable names specified are identical, but
thare are potential problems here.

While implementing this, I changed the fish behaviour in two separate ways:

* Previously, it was legal to supply more indexes than values while
slicing, e.g. 'set foo[ 1 3 7] bar'. The remaining indexes would be
silently to be empty strings. This could still be implemented, but I
felt that with the new set behavior the potential to hide bugs would
be too large so I dropped it.
* Erasing the last element of an array does not erase the array
itself. Previously, doing 'set -e foo[1]' if foo only contained one
element would erase the foo variable. Now it turns foo into an array
with zero elements. I think the new behaviour is more logical, which
is why I changed it.

The new code lives in the darcs tree as usual. Comments and ideas are welcome.

--
Axel


-------------------------------------------------------
Using Tomcat but need to do more? Need to support web services, security?
Get stuff done quickly with pre-integrated technology to make your job easier
Download IBM WebSphere Application Server v.1.0.1 based on Apache Geronimo
http://sel.as-us.falkag.net/sel?cmd=lnk&kid0709&bid&3057&dat1642
_______________________________________________
Fish-users mailing list
[email protected]
https://lists.sourceforge.net/lists/listinfo/fish-users

Reply via email to