Re: Why are there no ordered dictionaries?

2005-12-01 Thread Fuzzyman

Christoph Zwerschke wrote:


Hello Christoph,

 I think re-ordering will be a very rare use case anyway and slicing even
 more. As a use case, I think of something like mixing different
 configuration files and default configuration parameters, while trying
 to keep a certain order of parameters and parameters blocks.


In actual fact - being able to *reorder* the dictionary is the main way
I use this dictionary.

All the best,

Fuzzyman
http://www.voidspace.org.uk/python/index.shtml

 -- Christoph

-- 
http://mail.python.org/mailman/listinfo/python-list


Re: Why are there no ordered dictionaries?

2005-12-01 Thread Fuzzyman
Hmmm... it would be interesting to see if these tests can be used with
odict.

The odict implementation now has full functionality by the way.

Optimisations to follow and maybe a few *minor* changes.

Fuzzyman
http://www.voidspace.org.uk/python/index.shtml

-- 
http://mail.python.org/mailman/listinfo/python-list


Re: Why are there no ordered dictionaries?

2005-12-01 Thread Fuzzyman
 The semantics of assigning slices
 to d.keys[i:j] and d.values[i:j] are kind of tricky when the size changes
 and/or key names match or don't match in various ways, or the incoming
 data represents collapsing redundant keys that are legal sequential assignment
 overrides but change the size, etc.


I have come against the same problem with slice assignment, when doing
odict. :-)
Allowing the size to change prevents a useful optimisation - but I
dislike *preventing* programmers from doing things.

All the best,

Fuzzyman
http://www.voidspace.org.uk/python/index.shtml

 
 Regards,
 Bengt Richter

-- 
http://mail.python.org/mailman/listinfo/python-list


Re: Why are there no ordered dictionaries?

2005-12-01 Thread Bengt Richter
On 1 Dec 2005 03:53:27 -0800, Fuzzyman [EMAIL PROTECTED] wrote:

Hmmm... it would be interesting to see if these tests can be used with
odict.
I assume you are referring to the pytest tests I posted, though I would
need some of the context you snipped to me more sure ;-)

Anyway, with some changes[1], they can.


The odict implementation now has full functionality by the way.

The one at
http://www.voidspace.org.uk/cgi-bin/voidspace/downman.py?file=odict.py
? It seems to be unchanged.


Optimisations to follow and maybe a few *minor* changes.


Anyway, test of the above results in:

 C:\UTIL\\..\py.test  test
 = test process starts =
 testing-mode: inprocess
 executable:   d:\python-2.4b1\mingw\python24.exe  (2.4.0-beta-1)
 using py lib: D:\bpy24\py-0.8.0-alpha2\py rev unknown
 
 test\test_odicts.py[28] FF...FF....FFF..
 test\test_odicts_candidate.py[0]
 
 ___
 ___ entrypoint: test_sanity ___
 
 def test_sanity():
 d = CandidateDict()
 assert d.keys() == []
 assert d.values() == []
 assert d.items() == []
 assert d == d
 d = CandidateDict([(k,i*100) for i,k in enumerate('abcde')])
 E   assert repr(d) == %s([('a', 0), ('b', 100), ('c', 200), ('d', 300), 
('e', 400)])%Can
 dateDict.__name__
assert {'a': 0, 'b': 100, 'c': 200, 'd': 300, 'e': 400} == 
  (%s([('a', 0), ('b', 100
  ('c', 200), ('d', 300), ('e', 400)]) % CandidateDict.__name__)
  +  where {'a': 0, 'b': 100, 'c': 200, 'd': 300, 'e': 400} = 
repr({'a': 0, 'b': 100,
 c': 200, 'd': 300, 'e': 400})
 
 [C:\pywk\ut\test\test_odicts.py:19]
 ___
Apparently you are still using plain dict repr format, not a format that could 
(ideally) be exec'd
to reconstitute the thing repr'd.

  from  clp.odict import OrderedDict as CandidateDict
  CandidateDict.__name__
 'OrderedDict'
  repr(CandidateDict())
 '{}'

vs

  from  ut.creordict import Creordict as CandidateDict
  CandidateDict.__name__
 'Creordict'
  repr(CandidateDict())
 'Creordict([])'

Since the test uses CandidateDict.__name__, it should work either way.

 __ entrypoint: test___init__ __
 
 def test___init__():
 d = CandidateDict()
 assert d.keys() == []
 assert d.values() == []
 assert d.items() == []
 assert d == d
 d = CandidateDict([(k,i*100) for i,k in enumerate('abcde')])
 E   assert repr(d) == %s(%r)% (CandidateDict.__name__, d.items())
assert {'a': 0, 'b': 100, 'c': 200, 'd': 300, 'e': 400} == ('%s(%r)' 
  % ('OrderedDict
  [('a', 0), ('b', 100), ('c', 200), ('d', 300), ('e', 400)]))
  +  where {'a': 0, 'b': 100, 'c': 200, 'd': 300, 'e': 400} = 
repr({'a': 0, 'b': 100,
 c': 200, 'd': 300, 'e': 400})
 
 [C:\pywk\ut\test\test_odicts.py:32]
 ___
(Duplicate from test_sanity)

  entrypoint: test___delitem__ _
 
 def test___delitem__():
 d = CandidateDict([(k,i*100) for i,k in enumerate('abcde')])
 print mkresult('abcde')
 assert d == mkresult('abcde')
 ditems = d.items()
 print d['b']
 print d.items()
 del d['b']
 assert d ==  mkresult('acde')
 del d['a']
 assert d ==  mkresult('cde')
 del d['e']
 assert d ==  mkresult('cd')
 d = CandidateDict([(k,i*100) for i,k in enumerate('abcde')])
del d[1:3]
 
 [C:\pywk\ut\test\test_odicts.py:70]
 _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _
 
 def __delitem__(self, key):
 
  d = OrderedDict(((1, 3), (3, 2), (2, 1)))
  del d[3]
  d
 {1: 3, 2: 1}
  del d[3]
 Traceback (most recent call last):
 KeyError: 3
 
 # do the dict.__delitem__ *first* as it raises
 # the more appropriate error
 E   dict.__delitem__(self, key)
TypeError: unhashable type
 
 [c:\pywk\clp\odict.py:137]
 - - - - - - - - - - -  test___delitem__: recorded stdout - - - - - - - - - - -
 {'a': 0, 'b': 100, 'c': 200, 'd': 300, 'e': 400}
 100
 [('a', 0), ('b', 100), ('c', 200), ('d', 300), ('e', 400)]
 
 ___
You don't appear to accept slice operation syntax directly on the instance

 __ entrypoint: test___repr__ __
 
 def test___repr__():
 E   assert repr(CandidateDict()) == '%s([])'%CandidateDict.__name__
assert '{}' == ('%s([])' % CandidateDict.__name__)
  +  where '{}' = repr({})
  +where {} = CandidateDict()
 
 

Re: Why are there no ordered dictionaries?

2005-12-01 Thread Bengt Richter
On 1 Dec 2005 01:48:56 -0800, Fuzzyman [EMAIL PROTECTED] wrote:


Christoph Zwerschke wrote:


Hello Christoph,

 I think re-ordering will be a very rare use case anyway and slicing even
 more. As a use case, I think of something like mixing different
 configuration files and default configuration parameters, while trying
 to keep a certain order of parameters and parameters blocks.


In actual fact - being able to *reorder* the dictionary is the main way
I use this dictionary.

Curious as to usage patterns
1) how many instances created, deleted
2) how many elements in an instance min, max?
3) how often updated?
3a) just ordering, no value or size change?
3b) just value change, no order or size change?
3c) changes involving size?
4) proportions of read vs write/delete/reorder accesses?

Regards,
Bengt Richter
-- 
http://mail.python.org/mailman/listinfo/python-list


Re: Why are there no ordered dictionaries?

2005-11-29 Thread Bengt Richter
On Sun, 27 Nov 2005 12:00:23 +0100, Christoph Zwerschke [EMAIL PROTECTED] 
wrote:

Bengt Richter wrote:

d.keys[:] = newkeyseq
 
 Do you really mean just re-ordering the keys without a corresponding 
 reording of values??
 That would be a weird renaming of all values. Or do you means that any key 
 should still
 retrieve the same value as before if used as d[key]? In which case the 
 values must undergo
 the same permutation as the keys. I.e., you are assuming key-value pairings 
 remain stable
 through any key reorderings?

Since it is considered as being a dictionary in the first place, the 
key-value pairings should of course stay stable. In the usual 
implementation based on an ordinary dictionary with an additional key 
list (sequence in the Foord/Larosa and _keys in the Bejamin/Winter 
implementation), you would only set the key list, since the value list 
is generated dynamically. But if your implementation keeps internal 
values or items lists, these need to be adjusted as well.

I will assume that d has is a Foord/Larosa ordered dict with sequence 
attribute in the following.

Then, with other words,

d.keys[:] = newkeyseq

should do the same as:

d.sequence = newkeyseq

 Exactly what, though? should e.g.
 d.keys[3] =  newk3
 mean (not a suggested implementation, just to define semantics)
 keys = d.keys()
 if newk3 in keys and keys.index(newk3)!=3:
 raise ValueError,'Attempt to introduce duplicate key'
 items = d.items()
 items[3] = (newk3, items[3][1])
 d.clear()
 d.update(items)

Yes, that would be the correct semantics. Of course this should not be 
the real implementation and use KeyError instead of ValueError. With 
other words,

d.keys[i] = newkey

sould be the same as:

if d.sequence[i] != newkey:
 if newkey in d.sequence:
  raise KeyError,'Attempt to introduce duplicate key'
 else:
  d.sequence[i] = newkey

 This would allow what you might call renaming in place.
 Similarly
 d.keys[i:j] = newkeysij
 might have the semantics of
 keys = d.keys()
 outside = set(keys[:i])+set(keys[j:])
 if outside  set(newkeysij) or len(newkeysij) != len(set(newkeysij)):
 raise ValueError,'Attempt to introduce duplicate key(s)'
 items = d.items()
 items[i:j] = [(k, items[kx+i][1]) for kx,k in enumerate(newkeysij)]
 d.clear()
 d.update(items)
 
 Is this what is desired?

Not quite, because it does not preserve the key-value pairings (see 
above) and it would behave strangely or raise an exception if the new 
slice is larger. The following code would do:


keys = d.keys()
outside = set(keys[:i])|set(keys[j:])
if outside  set(newkeysij) or len(newkeysij) != len(set(newkeysij)):
 raise ValueError,'Attempt to introduce duplicate key(s)'
items = d.items()
items[i:j] = [(k, d.get(k, None)) for k in newkeysij]
d.clear()
d.update(items)

(Note that there was a bug in the second line. You cannot add sets.)
Oops, thinking about adding dicts ;-)


Again, this would be equivalent to:

seq = d.sequence
newseq = seq[:]
newseq[i:j] = newkeysij
if len(newseq) != len(set(newseq)):
 raise KeyError,'Attempt to introduce duplicate key(s)'
for k in set(seq[i:j]) - set(newkeysij):
 del d[k]
for k in set(newkeysij) - set(seq[i:j]):
 d[k] = None
d.sequence = newseq


You don't keep track of the item lists, they need to be built on every 
occasion.
 
 That depends on how you implement ;-)

Ok, I was thinking of the usual implementations.

 Back from holiday, so maybe I'll hack something out.

Let us know when you have something to check out.

Maybe Fuzzyman can make some moderate improvements to the existing 
odict.py, and you can do something more radical. Then we have two 
reference implementations and can compare how they prove regarding 
performance and usability.

My code so far is a kludge to get functionality. Perhaps we can arrive at
a spec by doing some TDD. My current kludge passes these tests
(run by py.test which I downloaded from the pypy project site and made
work (apparanently ;-) with IIRC a .pth file to point to py where I
expanded the zip, and a cmd file to kick of python running py.test,
and I think that was all there was. As you can see, it is super easy to define
tests. If you want to try it, I think I can retrace my steps and describe
the way I set it up (for windows NT) in a few turgid run-on paragraphs ;-)
Maybe I'll get around to writing a downloading/checking/installing script
for it, with a few interactive are-you-sure?'s and file tree placement options 
etc.

I'm calling it a Creordict for now -- Created-order-dict.
Here are the tests so far. Do you want to add some to refine what's supposed to
happen. You may want to look at test_items, test_keys, test_values
as those are the ones that provide d.items(), d.items[i], d.items[i:j]
style accesses, with assign, eval, and del available for the latter two.
also test___getitem__ for d[i] = value normal key access vs
d[i:j] = another Creordict 

Re: Why are there no ordered dictionaries?

2005-11-29 Thread Christoph Zwerschke
I had the same idea to create a py.test to verify and compare various 
implementations. The doctests in odict.py are nice, but you can't use 
them for this purpose and they may not test enough. It would be also 
good to have something for testing and comparing performance.

-- Christoph
-- 
http://mail.python.org/mailman/listinfo/python-list


Re: Why are there no ordered dictionaries?

2005-11-29 Thread Bengt Richter
On Tue, 29 Nov 2005 23:30:45 +0100, Christoph Zwerschke [EMAIL PROTECTED] 
wrote:

I had the same idea to create a py.test to verify and compare various 
implementations. The doctests in odict.py are nice, but you can't use 
them for this purpose and they may not test enough. It would be also 
good to have something for testing and comparing performance.

Well, the previous post test file just grew to make a simple check for various
aspects, so it's not super clean. I just grepped for defs in the implementation
and bulk appended test_ to make an empty starting point. Then I just filled
in tests after a preliminary sanity check test. But there are some things
that could still accidentally be inherited from the base class when builtin
utility functions are called on the dict object. Also there's a lot of cut-paste
duplication an no full explorations of corner cases. There's neat 
generator-based
test driving with different parameters that I didn't take advantage of,
etc. etc.

I should really read the py test docs and learn to use it
better if I am going to use it. But anyway, it's a qd hack to show and
sanity-check different usages. The semantics of assigning slices
to d.keys[i:j] and d.values[i:j] are kind of tricky when the size changes
and/or key names match or don't match in various ways, or the incoming
data represents collapsing redundant keys that are legal sequential assignment
overrides but change the size, etc.

One could add keyword args to the constructor to vary key eq and cmp used
on keys to determine key collisions between e.g. tuple keys and also for
sort. You could even allow partially non-hashable keys that way if you got 
tricky.
But maybe this is getting too tricky ;-)

I'll make some simple mods to the test to allow applying it to arbitrary
candidate implementations with different names and directory locations, so
I can try it on odict.py and other versions. But are the semantics right?

Doctest is handy, and in some ways I like examples showing up in the help docs,
but maybe help should take a keyword arg to select showing them (and some other
things too perhaps. A brief version excluding a lot of inheritance for classes
might be nice. Or a pattern for method and class var inclusion.

But I like the separation of the py.test tests with no need to mod the original.
Where next? This ordered dict thing is kind of a side-track from a side-track 
for me ;-)

Regards,
Bengt Richter
-- 
http://mail.python.org/mailman/listinfo/python-list


Re: Why are there no ordered dictionaries?

2005-11-27 Thread Christoph Zwerschke
Bengt Richter wrote:

d.keys[:] = newkeyseq
 
 Do you really mean just re-ordering the keys without a corresponding reording 
 of values??
 That would be a weird renaming of all values. Or do you means that any key 
 should still
 retrieve the same value as before if used as d[key]? In which case the values 
 must undergo
 the same permutation as the keys. I.e., you are assuming key-value pairings 
 remain stable
 through any key reorderings?

Since it is considered as being a dictionary in the first place, the 
key-value pairings should of course stay stable. In the usual 
implementation based on an ordinary dictionary with an additional key 
list (sequence in the Foord/Larosa and _keys in the Bejamin/Winter 
implementation), you would only set the key list, since the value list 
is generated dynamically. But if your implementation keeps internal 
values or items lists, these need to be adjusted as well.

I will assume that d has is a Foord/Larosa ordered dict with sequence 
attribute in the following.

Then, with other words,

d.keys[:] = newkeyseq

should do the same as:

d.sequence = newkeyseq

 Exactly what, though? should e.g.
 d.keys[3] =  newk3
 mean (not a suggested implementation, just to define semantics)
 keys = d.keys()
 if newk3 in keys and keys.index(newk3)!=3:
 raise ValueError,'Attempt to introduce duplicate key'
 items = d.items()
 items[3] = (newk3, items[3][1])
 d.clear()
 d.update(items)

Yes, that would be the correct semantics. Of course this should not be 
the real implementation and use KeyError instead of ValueError. With 
other words,

d.keys[i] = newkey

sould be the same as:

if d.sequence[i] != newkey:
 if newkey in d.sequence:
  raise KeyError,'Attempt to introduce duplicate key'
 else:
  d.sequence[i] = newkey

 This would allow what you might call renaming in place.
 Similarly
 d.keys[i:j] = newkeysij
 might have the semantics of
 keys = d.keys()
 outside = set(keys[:i])+set(keys[j:])
 if outside  set(newkeysij) or len(newkeysij) != len(set(newkeysij)):
 raise ValueError,'Attempt to introduce duplicate key(s)'
 items = d.items()
 items[i:j] = [(k, items[kx+i][1]) for kx,k in enumerate(newkeysij)]
 d.clear()
 d.update(items)
 
 Is this what is desired?

Not quite, because it does not preserve the key-value pairings (see 
above) and it would behave strangely or raise an exception if the new 
slice is larger. The following code would do:

keys = d.keys()
outside = set(keys[:i])|set(keys[j:])
if outside  set(newkeysij) or len(newkeysij) != len(set(newkeysij)):
 raise ValueError,'Attempt to introduce duplicate key(s)'
items = d.items()
items[i:j] = [(k, d.get(k, None)) for k in newkeysij]
d.clear()
d.update(items)

(Note that there was a bug in the second line. You cannot add sets.)

Again, this would be equivalent to:

seq = d.sequence
newseq = seq[:]
newseq[i:j] = newkeysij
if len(newseq) != len(set(newseq)):
 raise KeyError,'Attempt to introduce duplicate key(s)'
for k in set(seq[i:j]) - set(newkeysij):
 del d[k]
for k in set(newkeysij) - set(seq[i:j]):
 d[k] = None
d.sequence = newseq

You don't keep track of the item lists, they need to be built on every 
occasion.
 
 That depends on how you implement ;-)

Ok, I was thinking of the usual implementations.

 Back from holiday, so maybe I'll hack something out.

Let us know when you have something to check out.

Maybe Fuzzyman can make some moderate improvements to the existing 
odict.py, and you can do something more radical. Then we have two 
reference implementations and can compare how they prove regarding 
performance and usability.

-- Christoph
-- 
http://mail.python.org/mailman/listinfo/python-list


Re: Why are there no ordered dictionaries?

2005-11-27 Thread Christoph Zwerschke
Christoph Zwerschke wrote:

 I will assume that d has is a Foord/Larosa ordered dict with sequence 
 attribute in the following.
 
 Then, with other words,
 
 d.keys[:] = newkeyseq
 
 should do the same as:
 
 d.sequence = newkeyseq

At least in the case where newkeyseq is a permutation of d.sequence.

Otherwise, it should behave like the given implementation for setting 
slices, i.e.

- if newkeyseq has duplicate elements, an exception should be raised.
- if newkeyseq has elements not in d.sequence, then the dictionary 
should be updated with corresponding None values
- if d.sequence has elements not in newkeyseq then these elements should 
be deleted from the dictionary

-- Christoph
-- 
http://mail.python.org/mailman/listinfo/python-list


Re: Why are there no ordered dictionaries?

2005-11-27 Thread Fuzzyman
Note that I've done two things with the Foord/Larosa dict. ;-)

I've implemented slicing, including slice assignment and deletion. I've
also 'hidden' ``sequence``, but you can pass arguments to keys, values
and items.

I've done a second (experimental) implementation of a custom keys
object. This is effectively the managed list - which you can call as a
method or mutate in place. You can't delete members from 'keys' but you
can do slice assignment so long as the sequence you're replacing is the
same length (and is a re -ordering of the set being replaced).

I'll post it on Monday, and if people like it I'll complete it.

All the best,


Fuzzyman
http://www.voidspace.org.uk/python/index.shtml

-- 
http://mail.python.org/mailman/listinfo/python-list


Re: Why are there no ordered dictionaries?

2005-11-27 Thread Christoph Zwerschke
Bengt Richter schrieb:

 OTOH,
   {}[:]
  Traceback (most recent call last):
File stdin, line 1, in ?
  TypeError: unhashable type
 I.e., slices are not valid keys for ordinary dicts, and slices tie in
 very well with the ordered aspect of ordered dicts, so that's an
 argument for permitting it via the indexing syntax, not just items[:]
 or items()[:] which have related but not identical semantics.

I see it like that. BTW, the above error message is pretty bad.

  I wonder who is going to use it for what.

I think re-ordering will be a very rare use case anyway and slicing even 
more. As a use case, I think of something like mixing different 
configuration files and default configuration parameters, while trying 
to keep a certain order of parameters and parameters blocks.

-- Christoph
-- 
http://mail.python.org/mailman/listinfo/python-list


Re: Why are there no ordered dictionaries?

2005-11-26 Thread Bengt Richter
On Thu, 24 Nov 2005 18:42:45 +0100, Christoph Zwerschke [EMAIL PROTECTED] 
wrote:

Bengt Richter schrieb:

d.setvalues((13, 14)) == d = OrderedDict((1, 13), (2, 14))

 The implication above is that OrderedDict takes an *args argument,
 but really it takes a single argument that is a sequence of k,v pairs,
 (and maybe some keyword options).

Right. Interpret it as a short notation only, I did not want to change 
the interface. I think it's a common mistake to forget the brackets 
because you think one pair should be enough. At least I often forget it.
Ok, I forget this too.

 You could make keys, values, and items custom descriptors which would define 
 __call__
 for the old key() etc accesses, well as __getitem__ and __setitem__. Then 
 you could write
 
 d.items[0], d.items[-1] = d.items[-1], d.items[0]
 
 to swap the order of the first and last items in the thing (I hesitate to 
 say dict ;-)
 You could also operate on slices.

Nice. You could also get the i-th value with d.values[i].

But is this considered good style or would it be considered dirty to 
have a callable member that also supports indexing and slicing? (I don't 
know, just asking?) Plus, it opens a can of worms by increasing the 
complexity tremendously. Let's see whether this can be handled.
I suspect not that complex, but it has the same performance disadvantage as
properties.


 BTW, before I showed an example where d[2:3] returned
 a new dict instance rather than d.items()[:]. I think the items list
  is better, since they naturally add, sort, reverse, etc as lists,
  and you can write OrderedDict(d[2:3]+d[1:2]) if you want a new dict.

Not sure about that. I would rather expect that if you slice an object, 
you get an object of the same type. And you can also add, sort, reverse, 
etc the ordered dict if you want.

 A slice assignment to d[i:j] is really sugar for something, but we have to 
 decide exactly
 what in case of duplicate keys in the incoming items, either with each other 
 ...

You mean slice assignments to d.items[i:j]. If you make the slice 
assignment to d[i:j] then at least you cannot have conflicts in the 
incoming items. The first question is: Should a slice assignment be 
treated as deletion with subsequential addition (changing the order) or 
as a replacement (i.e. try to not change the order)? I agree that the 
second would be the expected semantics, but as you mentioned more 
difficult to implement.

  One way to define it would be
  d.items[i:j] = itemseq
 
 to be implemented as sugar for
 newitems = d.items[:i] + list(itemseq) + d.items[j:]
 d.clear()
 d.update(newitems)

Which should be the same as
d = OrderedDict(d.items[:i] + list(itemseq) + d.items[j:])
Sounds reasonable.
Actually it's not the same, which is why I wrote it with update.
Analogous to slice assignment in lists, the referred-to object
gets mutated. Hence preexisting references to the object see the change too.

If you just rebind d with a new OrderedDict object, previous bindings
are not affected. I.e.,
   d = OrderedDict(sorted((k,i)) for i,k in enumerate('abc'))
   e = d
   d = OrderedDict(d.items[:1] + [('b', 100)] + d.items[2:])
   d.items()[1] # = ('b', 100)
   e.items()[1] # = ('b', 1)   # unaffected



 So
 d.reverse()
 could be spelled
 d.items[:] = d.items[::-1]

Slice assignment for keys and values would also allow to set a new key 
order with

d.keys[:] = newkeyseq
Do you really mean just re-ordering the keys without a corresponding reording 
of values??
That would be a weird renaming of all values. Or do you means that any key 
should still
retrieve the same value as before if used as d[key]? In which case the values 
must undergo
the same permutation as the keys. I.e., you are assuming key-value pairings 
remain stable
through any key reorderings?


So no need to define a setkeys() method or let keys() take arguments.
If we want to allow this kind of things at all.

 If you are using slices, you can safely use them directly in the __getitem__ 
 of th dict interface,
 as I did in the Que mas? post. So we don't have to write d.items[i:j] and 
 could write d[i:j].
 The thing is, d[i:j] will tempt to skip .items in d.items[i] and write 
 d[i], which has the dict
  key meaning, not the item list index. It is faster not have a 
descriptor between though.

I still think d[i:j] should return an ordered dict, not an item list.
Easy to do either way.


 I think maybe allowing write to keys or values is pretty iffy. There are too 
 many weird
 re-associations of keys and values possible, and which you could do my other 
 means if you
 really really wanted to. But I do think full index and slice read access 
 would be fine.

There are different opinions. Fuzzyman would probably say Don't trust 
yourself? I myself am undecided. Perhaps you could expect that somebody 
knows what he does if he makes a slice assignment to d.keys. In any way, 
such an assignment should not break the directory (with 

Re: Why are there no ordered dictionaries?

2005-11-26 Thread Bengt Richter
On Fri, 25 Nov 2005 19:42:49 +, Tom Anderson [EMAIL PROTECTED] wrote:

On Wed, 23 Nov 2005, Carsten Haese wrote:

 On Wed, 2005-11-23 at 15:17, Christoph Zwerschke wrote:
 Bengt Richter wrote:

  E.g., it might be nice to have a mode that assumes d[key] is
 d.items()[k][1] when
  key is an integer, and otherwise uses dict lookup, for cases where
 the use
  case is just string dict keys.

 I also thought about that and I think PHP has that feature, but it's 
 probably better to withstand the temptation to do that. It could lead 
 to an awful confusion if the keys are integers.

 Thus quoth the Zen of Python:
 Explicit is better than implicit.
 In the face of ambiguity, refuse the temptation to guess.

 With those in mind, since an odict behaves mostly like a dictionary, [] 
 should always refer to keys. An odict implementation that wants to allow 
 access by numeric index should provide explicitly named methods for that 
 purpose.

+1

Overloading [] to sometimes refer to keys and sometimes to indices is a 
really, really, REALLY bad idea. Let's have it refer to keys, and do 
indices either via a sequence attribute or the return value of items().

More generally, if we're going to say odict is a subtype of dict, then we 
have absolutely no choice but to make the methods that it inherits behave 
the same way as in dict - that's what subtyping means. That means not 
doing funky things with [], returning a copy from items() rather than a 
live view, etc.

OTOH,
  {}[:]
 Traceback (most recent call last):
   File stdin, line 1, in ?
 TypeError: unhashable type
I.e., slices are not valid keys for ordinary dicts, and slices tie in
very well with the ordered aspect of ordered dicts, so that's an
argument for permitting it via the indexing syntax, not just items[:]
or items()[:] which have related but not identical semantics.

So, how do we provide mutatory access to the order of items? Of the 
solutions discussed so far, i think having a separate attribute for it - 
like items, a live view, not a copy (and probably being a variable rather 
than a method) - is the cleanest, but i am starting to think that 
overloading items to be a mutable sequence as well as a method is quite 
neat. I like it in that the it combines two things - a live view of the 
order and a copy of the order - that are really two aspects of one thing, 
which seems elegant. However, it does strike me as rather unpythonic; it's 
trying to cram a lot of functionality in an unexpected combination into 
one place. Sparse is better than dense and all that. I guess the thing to 
do is to try both out and see which users prefer.

I wonder who is going to use it for what.

Regards,
Bengt Richter
-- 
http://mail.python.org/mailman/listinfo/python-list


Re: Why are there no ordered dictionaries?

2005-11-25 Thread Fuzzyman

Christoph Zwerschke wrote:
 Fuzzyman schrieb:
  d.keys() will still return a copy of the list, so d.keys()[i] will
  still be slower than d.sequence[i]

 Right, I forgot that.  Bengt suggested to implement __call__ as well as
 __getitem__ and __setitem__ for keys, values and items.

 In this case, you could very effectively access it as d.values[i].


That means making keys, values, and items custom objects.
Creating a new instance would have the overhead of creating 4 new
objects instead of just 1. Is the added convenience worth it ? (Plus
the extra layers of method calls for each access).

I'm not sure. It's a nice idea in terms of using it (we could just
leave the sequence attribute as an alias for the new keys attribute -
for backwards compatibility).

All the best,



Fuzzyman
http://www.voidspace.org.uk/python/index.shtml

 -- Christoph

-- 
http://mail.python.org/mailman/listinfo/python-list


Re: Why are there no ordered dictionaries?

2005-11-25 Thread Christoph Zwerschke
Le ruego me perdone.

replace('haber', random.choice('tener', 'hacer', 'lograr'))

Mi espanol es peor que mi python.

-- Christoph
-- 
http://mail.python.org/mailman/listinfo/python-list


Re: Why are there no ordered dictionaries?

2005-11-25 Thread Fuzzyman
Sure - that was just an example of mutating the keys list without
having direct access to it.

If keys was implemented as an object (with a ``__call__`` method) then
we could also implement sequence methods on it - making it easier to
mutate the keys/values/items directly.

All the best,

Fuzzyman
http://www.voidspace.org.uk/python/index.shtml

-- 
http://mail.python.org/mailman/listinfo/python-list


Re: Why are there no ordered dictionaries?

2005-11-25 Thread Fuzzyman

Alex Martelli wrote:
 Fuzzyman [EMAIL PROTECTED] wrote:

  There is already an update method of course. :-)
 
  Slicing an ordered dictionary is interesting - but how many people are
  actually going to use it ? (What's your use case)

 I detest and abhor almost-sequences which can't be sliced (I consider
 that a defect of collections.deque).  If the ordered dictionary records
 by its sequencing the time order of key insertion, being able to ask for
 the last 5 keys entered or the first 3 keys entered seem to me to be
 perfectly natural use cases, and most naturally accomplished by slicing
 of course, d[-5:] and d[:3] respectively.


If you slice an ordered dictionary, I assume you would expect to get an
ordered dictionary back ?

Fuzzyman
http://www.voidspace.org.uk/python/index.shtml

 
 Alex

-- 
http://mail.python.org/mailman/listinfo/python-list


Re: Why are there no ordered dictionaries?

2005-11-25 Thread Fuzzyman
Sure - that was just an example of mutating the keys list without
having direct access to it.

If keys was implemented as an object (with a ``__call__`` method) then
we could also implement sequence methods on it - making it easier to
mutate the keys/values/items directly.

All the best,

Fuzzyman
http://www.voidspace.org.uk/python/index.shtml

-- 
http://mail.python.org/mailman/listinfo/python-list


Re: Why are there no ordered dictionaries?

2005-11-25 Thread Christoph Zwerschke
Fuzzyman wrote:

 That means making keys, values, and items custom objects.
 Creating a new instance would have the overhead of creating 4 new
 objects instead of just 1. Is the added convenience worth it ? (Plus
 the extra layers of method calls for each access).

I'm not sure about that either. But since you are using odict for 
convenience reasons anyway, and not for performance reasons, it would be 
consequential. Performance testing should be made anyway, so this could 
be tested as well. I think that creating these 3 additional objects will 
not matter much if the dict has more than a handful of items. And the 
extra layers will be only called if you really access these keys, values 
or items attributes which will not happen very frequently. Normally, you 
just loop over an ordered directory and acess keyed values.

 I'm not sure. It's a nice idea in terms of using it (we could just
 leave the sequence attribute as an alias for the new keys attribute -
 for backwards compatibility).

Yes, you could make it a deprecated feature.

-- Christoph
-- 
http://mail.python.org/mailman/listinfo/python-list


Re: Why are there no ordered dictionaries?

2005-11-25 Thread Alex Martelli
Fuzzyman [EMAIL PROTECTED] wrote:
   ...
 If you slice an ordered dictionary, I assume you would expect to get an
 ordered dictionary back ?

That would be helpful, yes, though there are precedents for types whose
slicing doesn't return an instance of that type (e.g. slices of an mmap
are instances of str, not of mmap, if I recall correctly), most
sliceable sequences do follow that pattern.


Alex
-- 
http://mail.python.org/mailman/listinfo/python-list


Re: Why are there no ordered dictionaries?

2005-11-25 Thread Tom Anderson
On Wed, 23 Nov 2005, Christoph Zwerschke wrote:

 Alex Martelli wrote:

 However, since Christoph himself just misclassified C++'s std::map as 
 ordered (it would be sorted in this new terminology he's now 
 introducing), it seems obvious that the terminological confusion is 
 rife.

 Speaking about ordered and sorted in the context of collections is 
 not a new terminology I am introducing, but seems to be pretty common in 
 computer science

This is quite true. I haven't seen any evidence for 'rife' 
misunderstanding of these terms.

That said ...

 Perhaps Pythonists are not used to that terminology, since they use the 
 term list for an ordered collection. An ordered dictionary is a 
 dictionary whose keys are a (unique) list. Sometimes it is also called a 
 sequence

Maybe we should call it a 'sequenced dictionary' to fit better with 
pythonic terminology?

tom

-- 
YOU HAVE NO CHANCE TO ARRIVE MAKE ALTERNATIVE TRAVEL ARRANGEMENTS. --
Robin May
-- 
http://mail.python.org/mailman/listinfo/python-list


Re: Why are there no ordered dictionaries?

2005-11-25 Thread Tom Anderson
On Wed, 23 Nov 2005, Carsten Haese wrote:

 On Wed, 2005-11-23 at 15:17, Christoph Zwerschke wrote:
 Bengt Richter wrote:

  E.g., it might be nice to have a mode that assumes d[key] is
 d.items()[k][1] when
  key is an integer, and otherwise uses dict lookup, for cases where
 the use
  case is just string dict keys.

 I also thought about that and I think PHP has that feature, but it's 
 probably better to withstand the temptation to do that. It could lead 
 to an awful confusion if the keys are integers.

 Thus quoth the Zen of Python:
 Explicit is better than implicit.
 In the face of ambiguity, refuse the temptation to guess.

 With those in mind, since an odict behaves mostly like a dictionary, [] 
 should always refer to keys. An odict implementation that wants to allow 
 access by numeric index should provide explicitly named methods for that 
 purpose.

+1

Overloading [] to sometimes refer to keys and sometimes to indices is a 
really, really, REALLY bad idea. Let's have it refer to keys, and do 
indices either via a sequence attribute or the return value of items().

More generally, if we're going to say odict is a subtype of dict, then we 
have absolutely no choice but to make the methods that it inherits behave 
the same way as in dict - that's what subtyping means. That means not 
doing funky things with [], returning a copy from items() rather than a 
live view, etc.

So, how do we provide mutatory access to the order of items? Of the 
solutions discussed so far, i think having a separate attribute for it - 
like items, a live view, not a copy (and probably being a variable rather 
than a method) - is the cleanest, but i am starting to think that 
overloading items to be a mutable sequence as well as a method is quite 
neat. I like it in that the it combines two things - a live view of the 
order and a copy of the order - that are really two aspects of one thing, 
which seems elegant. However, it does strike me as rather unpythonic; it's 
trying to cram a lot of functionality in an unexpected combination into 
one place. Sparse is better than dense and all that. I guess the thing to 
do is to try both out and see which users prefer.

tom

-- 
YOU HAVE NO CHANCE TO ARRIVE MAKE ALTERNATIVE TRAVEL ARRANGEMENTS. --
Robin May
-- 
http://mail.python.org/mailman/listinfo/python-list


Re: Why are there no ordered dictionaries?

2005-11-25 Thread Tom Anderson
On Wed, 23 Nov 2005, Christoph Zwerschke wrote:

 Tom Anderson wrote:

 I think it would be probably the best to hide the keys list from the 
 public, but to provide list methods for reordering them (sorting, slicing 
 etc.).

 one with unusual constraints, so there should be a list i can manipulate in 
 code, and which should of course be bound by those constraints.

 Think of it similar as the case of an ordinary dictionary: There is 
 conceptually a set here (the set of keys), but you cannot manipulate it 
 directly, but only through the according dictionary methods.

Which is a shame!

 For an ordedred dictionary, there is conceptually a list (or more 
 specifically a unique list). Again you should not manipulate it 
 directly, but only through methods of the ordered dictionary.

 This sounds at first more complicated, but is in reality more easy.

 For instance, if I want to put the last two keys of an ordered dict d at 
 the beginning, I would do it as d = d[:-2] + d[-2:].

As i mentioned elsewhere, i think using [] like this is a terrible idea - 
and definitely not easier.

 With the list attribute (called sequence in odict, you would have to 
 write: d.sequence = d.sequence[:-2] + d.sequence[-2:]. This is not only 
 longer to write down, but you also have to know that the name of the 
 attribute is sequence.

True, but that's not exactly rocket science. I think the rules governing 
when your [] acts like a dict [] and when it acts like a list [] are 
vastly more complex than the name of one attribute.

 Python's strength is that you don't have to keep many details in mind 
 because it has a small basic vocabulary and orthogonal use.

No it isn't - it's in having a wide set of basic building blocks which do 
one simple thing well, and thus which are easy to use, but which can be 
composed to do more complex things. What are other examples of this kind 
of 'orthogonal use'?

 I prefer the ordered dictionary does not introduce new concepts or 
 attributes if everything can be done intuitively with the existing 
 Python methods and operators.

I strongly agree. However, i don't think your overloading of [] is at all 
intuitive.

tom

-- 
YOU HAVE NO CHANCE TO ARRIVE MAKE ALTERNATIVE TRAVEL ARRANGEMENTS. --
Robin May
-- 
http://mail.python.org/mailman/listinfo/python-list


Re: Why are there no ordered dictionaries?

2005-11-25 Thread Christoph Zwerschke
Tom Anderson schrieb:

 Maybe we should call it a 'sequenced dictionary' to fit better with 
 pythonic terminology?

That's not such a bad idea. Note that it is called like that in the 
Python version of the Programming Language Examples Alike Cookbook:

http://pleac.sourceforge.net/pleac_python/hashes.html#AEN250

Anyway, I still favor the more common term ordered dictionary.

-- Christoph
-- 
http://mail.python.org/mailman/listinfo/python-list


Re: Why are there no ordered dictionaries?

2005-11-25 Thread Christoph Zwerschke
It seems everybody is in full agreement here.

I have the same mixed feeling about letting keys/values/items become 
both managed list attributes and still returning copies of the lists 
when called in the usual way as methods.

I don't know any precedent for doing things that way and i'm unsure 
whether it meets the Zen of Python. But anyway the idea is nice enough 
to try it out.

-- Chris
-- 
http://mail.python.org/mailman/listinfo/python-list


Re: Why are there no ordered dictionaries?

2005-11-25 Thread Christoph Zwerschke
Tom Anderson wrote:

 True, but that's not exactly rocket science. I think the rules governing 
 when your [] acts like a dict [] and when it acts like a list [] are 
 vastly more complex than the name of one attribute.

I think it's not really rocket science either to assume that an ordered 
dictionary behaves like a dictionary if you access items by subscription 
and like a list if you use slices (since slice indexes must evaluate to 
integers anyway, they can only be used as indexes, not as keys).

 Python's strength is that you don't have to keep many details in mind 
 because it has a small basic vocabulary and orthogonal use.

 No it isn't - it's in having a wide set of basic building blocks which 
 do one simple thing well, and thus which are easy to use, but which can 
 be composed to do more complex things.  What are other examples of this
  kind of 'orthogonal use'?

I mean for instance that you can deal with a tuple in the same way as 
with a string and things like that. Concerning small: Somebody coined 
the good slogan Python fits my brain but I could also say Python fits 
*into* my brain (I mean without the batteries of course ;-) - you 
pretty soon have all the built-in functins, datatypes and their use in 
your head. On the other side of course, Python is a huge field and you 
can discuss endlessly as we are doing here.

Anyway, my argument was not good (avoiding new attributes names in order 
to keep the vocabulary small).

And by the way, what both of us listed as strengths of Python will be 
probably claimed by protagonists of any other language as well.

-- Christoph
-- 
http://mail.python.org/mailman/listinfo/python-list


Re: Why are there no ordered dictionaries?

2005-11-25 Thread Tom Anderson
On Fri, 25 Nov 2005, Christoph Zwerschke wrote:

 Tom Anderson wrote:

 True, but that's not exactly rocket science. I think the rules governing 
 when your [] acts like a dict [] and when it acts like a list [] are vastly 
 more complex than the name of one attribute.

 I think it's not really rocket science either to assume that an ordered 
 dictionary behaves like a dictionary if you access items by subscription 
 and like a list if you use slices (since slice indexes must evaluate to 
 integers anyway, they can only be used as indexes, not as keys).

When you put it that way, it makes a certain amount of sense - [:] is 
always about index, and [] is always about key. It's still icky, but it is 
completely unambiguous.

tom

-- 
I content myself with the Speculative part [...], I care not for the
Practick. I seldom bring any thing to use, 'tis not my way. Knowledge
is my ultimate end. -- Sir Nicholas Gimcrack
-- 
http://mail.python.org/mailman/listinfo/python-list


Re: Why are there no ordered dictionaries?

2005-11-24 Thread Fuzzyman

Alex Martelli wrote:
 Fuzzyman [EMAIL PROTECTED] wrote:
...
   - the internal keys list should be hidden
 
  I disagree. It is exposed so that you can manually change the order
  (e.g. to create a sorted dict, rather than one ordered by key
  insertion).
 
  What do you *gain* by hiding it ?

 Freedom of implementation, of course.  E.g., I can perhaps get better
 performance by keeping a red-black tree of (insertiontime,key) pairs, so
 for example deleting a key is O(log(N)) rather than O(N) as it would
 have to be if the sequence had to be kept as a Python list.

 What ELSE do you ever gain by enforcing abstraction and information
 hiding?  Conceptual integrity and implementation freedom...


The poster I was replying to inferred that we should hide it to protect
him from breaking it. :-)

Your reason is much more valid than the one I inferred. (And probably
worth chanign the code for).


   - list methods should be mixed in instead
 
  Hmm... I did consider this. Which list methods would you consider
  appropriate ?
 
  The difficulty is that integers are valid keys for a dictionary.
  Perhaps a subclass that uses integers as indexes instead...

 What about allowing slicing, taking advantage of the fact that slices
 are NOT valid dictionary keys?

Hmm... ok, simple enough to implement. What would anyone *use* it for
though ?

 Presumably sort and reverse methods are also desired.


Yeah - good idea. Insert is also good - I can't remember if we provide
this or not.

Thanks


Fuzzyman
http://www.voidspac.org.uk/python/index.shtml

  You can always perform list operations on the ``sequence`` attribute of
  course.

 But NOT having to expose .sequence as a real mutable list whose changes
 affect ordering has many advantages, as above noticed.
 
 
 Alex

-- 
http://mail.python.org/mailman/listinfo/python-list


Re: Why are there no ordered dictionaries?

2005-11-24 Thread Fuzzyman
Ok.

That answers a question in the post I've just made. This thread is hard
to follow.

Thanks

Fuzzyman
http://www.voidspace.org.uk/python/index.shtml

-- 
http://mail.python.org/mailman/listinfo/python-list


Re: Why are there no ordered dictionaries?

2005-11-24 Thread Fuzzyman

Christoph Zwerschke wrote:
 Fuzzyman wrote:

  So what do you want returned when you ask for d1[1] ? The member keyed
  by 1, or the item in position 1 ?

 In case of conflict, the ordered dictionary should behave like a
 dictionary, not like a list. So d1[1] should be the member keyed by 1,
 not the item in position 1. Only in case there is no member keyed by 1,
 the item in position 1 could be returned, but I think that would be too
 adventurous a hattrick and can lead to big confusion. Better to raise a
 KeyError in that case.


I agree - hard to trace bugs lie this way

[snip..]

 Instead of writing d.sequence = new_sequence, I would write
 d.setkeys(new_sequence). But I'm not sure what to do if new_sequence is
 not a permutation of the old one. Raise a KeyError? Or even swallow
 this? For instance


This is an interesting question - I don't know which is the best
behaviour here.

It's probably better to raise a KeyError - that way the error will
occur when it happens.

The simplest way of doing this is to check that the new key list
(sorted) is the same as the original one (sorted). This is potentially
quite an expensive operation.

It might be faster to compare sets with Python 2.4 - but we intend to
retain compatibility with Python 2.2.

 d = OrderedDict((1,11), (2,12))

 d.setkeys((2, 1)) == d = OrderedDict((2, 11), (1, 12))

 d.setkeys((3, 4)) == d = OrderedDict((3, 11), (4, 12)) (or KeyError?)

 d.setvalues((12, 11)) == d = OrderedDict((1, 12), (2, 11))

 d.setvalues((13, 14)) == d = OrderedDict((1, 13), (2, 14)) (always ok)

 (Or maybe better set_keys in analogy to has_key?)

 I hesitate making keys and values managed properties, because this would
 conflict with them being methods in ordinary dicts. Ordered dicts should
 resemble ordinary dicts as closely as possible. And giving it a
 different name like sequence I find confusing and unintuitive.


You really want to be able to set values as a sequence ? I suppose it's
even easier to implement than changing keys, but I'd never considered
it.

 A resort could be the following: If keys() is given a sequence as
 argument, then use this as the new sequence of keys, and similar with
 values(). This way, no new methods need to be introduced.


That's not a bad idea. I'll chat with Nicola Larosa and see what he
thinks.

It does break backawards compatibility of course...

All the best,

Fuzzyman
http://www.voidspace.org.uk/python/index.shtml

 -- Christoph

-- 
http://mail.python.org/mailman/listinfo/python-list


Re: Why are there no ordered dictionaries?

2005-11-24 Thread Duncan Booth
Christoph Zwerschke wrote:

 Duncan Booth schrieb:
 In Javascript Object properties (often used as an associative array)
 are defined as unordered although as IE seems to always store them in
 the order of original insertion it wouldn't surprise me if there are
 a lot of websites depending on that behaviour.
 
 You're right with both. The ECMA language definition says object 
 properties are an unordered collection, but MSIE and probably other 
 browsers keep the order in which they were created. Of course one
 should not rely on that.
 
Yes, the real fun bit is arrays. If you create an array using the 'new 
Array' or [ ... ] then a for..in loop might well trick you into thinking it 
is going to go through the elements in order, but if you assign to elements 
directly it breaks down:

a = ['a', 'b', 'c'];
a[4] = 'e';
a[3] = 'd';
for (var k in a) {
  alert(a[k]+'='+a[k]);
}

On IE this will go through elements in the order 0, 1, 2, 4, 3.

Also, it is original order of insertion which matters, not the 'last 
in/last out' you might have expected. In other words it looks rather as 
though IE simply sets deleted properties to undefined (and skips them on 
iteration), it never really deletes a property, so anyone who tries to use 
a Javascript object as an associative array with lots of rapidly changing 
keys could be in for a nasty shock.
-- 
http://mail.python.org/mailman/listinfo/python-list


Re: Why are there no ordered dictionaries?

2005-11-24 Thread Fuzzyman

Carsten Haese wrote:
 On Wed, 23 Nov 2005 23:39:22 +0100, Christoph Zwerschke wrote
  Carsten Haese schrieb:
 
   Thus quoth the Zen of Python:
   Explicit is better than implicit.
   In the face of ambiguity, refuse the temptation to guess.
  
   With those in mind, since an odict behaves mostly like a dictionary, []
   should always refer to keys. An odict implementation that wants to allow
   access by numeric index should provide explicitly named methods for that
   purpose.
 
  Exactly. But I don't think in this case such methods would be
  needed. You easily get the i-th value in the ordered dict as
  d.values()[i].
 
  -- Chris

 True enough, but unless the odict has its list of values on hand, you're
 asking the odict to build a list of all its values just so that you can get
 the i'th element. Having a method that does the equivalent of d[d.sequence[i]]
 would be cleaner and more efficient.


I'm going to add some of the sequence methods. I'm *not* going to allow
indexing, but I will allow slicing.

You can also do d[d.keys()[i]]

This provides two ways of fetching values by index, so I don't want to
add another.

All the best,

Fuzzyman
http://www.voidspace.org.uk/python/index.shtml
 -Carsten

-- 
http://mail.python.org/mailman/listinfo/python-list


Re: Why are there no ordered dictionaries?

2005-11-24 Thread Piet van Oostrum
 Christoph Zwerschke [EMAIL PROTECTED] (CZ) escribió:

CZ Eso es exactamente lo que yo queria haber!

¿Haber? ¿Tener? :=(
-- 
Piet van Oostrum [EMAIL PROTECTED]
URL: http://www.cs.uu.nl/~piet [PGP 8DAE142BE17999C4]
Private email: [EMAIL PROTECTED]
-- 
http://mail.python.org/mailman/listinfo/python-list


Re: Why are there no ordered dictionaries?

2005-11-24 Thread Fuzzyman
By the way, Nicola and I will be working on an improving odict in line
with several of the suggestions in this thread.

See :
http://www.voidspace.org.uk/python/weblog/arch_d7_2005_11_19.shtml#e140

All the best,

Fuzzyman
http://www.voidspace.org.uk/python/index.shtml

-- 
http://mail.python.org/mailman/listinfo/python-list


Re: Why are there no ordered dictionaries?

2005-11-24 Thread Christoph Zwerschke
Duncan Booth schrieb:
 On IE this will go through elements in the order 0, 1, 2, 4, 3.

Oops! I bet most people would not expect that, and it is probably not 
mentioned in most Javascript tutorials. I think this is a weakpoint of 
the ECMA definition, not MSIE.

-- Christoph
-- 
http://mail.python.org/mailman/listinfo/python-list


Re: Why are there no ordered dictionaries?

2005-11-24 Thread Fuzzyman

Tom Anderson wrote:
 On Tue, 22 Nov 2005, Christoph Zwerschke wrote:

  One implementation detail that I think needs further consideration is in
  which way to expose the keys and to mix in list methods for ordered
  dictionaries.
 
  In Foord/Larosa's odict, the keys are exposed as a public member which
  also seems to be a bad idea (If you alter the sequence list so that it
  no longer reflects the contents of the dictionary, you have broken your
  OrderedDict).
 
  I think it would be probably the best to hide the keys list from the public,
  but to provide list methods for reordering them (sorting, slicing etc.).

 I'm not too keen on this - there is conceptually a list here, even if it's
 one with unusual constraints, so there should be a list i can manipulate
 in code, and which should of course be bound by those constraints.


I think I am now in favour of hiding hte sequence attribute.

You will be able to mutate the the keys list through :

d1 = OrderedDict(some_sequence_of_items)
keys = d1.keys()
keys.sort() # or other mutation
d1.keys(keys)

Admittedly this is a lot slower than :

d1 = OrderedDict(some_sequence_of_items)
d1.sequence.sort()

*but* it frees the squence attribute from any implementation details.

All the best,

Fuzzyman
http://www.voidspace.org.uk/python/index.shtml

 I think the way to do it is to have a sequence property (which could be a
 managed attribute to prevent outright clobberation) which walks like a
 list, quacks like a list, but is in fact a mission-specific list subtype
 whose mutator methods zealously enforce the invariants guaranteeing the
 odict's integrity.

 I haven't actually tried to write such a beast, so i don't know if this is
 either of possible and straightforward.

 tom

 --
 When I see a man on a bicycle I have hope for the human race. --
 H. G. Wells

-- 
http://mail.python.org/mailman/listinfo/python-list


Re: Why are there no ordered dictionaries?

2005-11-24 Thread Bengt Richter
On Wed, 23 Nov 2005 23:00:29 +0100, Christoph Zwerschke [EMAIL PROTECTED] 
wrote:

Fuzzyman wrote:

 So what do you want returned when you ask for d1[1] ? The member keyed
 by 1, or the item in position 1 ?

In case of conflict, the ordered dictionary should behave like a 
dictionary, not like a list. So d1[1] should be the member keyed by 1, 
not the item in position 1. Only in case there is no member keyed by 1, 
the item in position 1 could be returned, but I think that would be too 
adventurous a hattrick and can lead to big confusion. Better to raise a 
KeyError in that case.

 But no other way to directly manipulate the keys should be provided.

 Why - don't trust yourself with it ?

No, because I think it is not needed if list operations like insert are 
directly possible on your dictionary.

But maybe methods such as setkeys() and setvalues() would be nice to 
have in addition.

Instead of writing d.sequence = new_sequence, I would write 
d.setkeys(new_sequence). But I'm not sure what to do if new_sequence is 
not a permutation of the old one. Raise a KeyError? Or even swallow 
this? For instance

d = OrderedDict((1,11), (2,12))

d.setkeys((2, 1)) == d = OrderedDict((2, 11), (1, 12))

d.setkeys((3, 4)) == d = OrderedDict((3, 11), (4, 12)) (or KeyError?)

d.setvalues((12, 11)) == d = OrderedDict((1, 12), (2, 11))

d.setvalues((13, 14)) == d = OrderedDict((1, 13), (2, 14)) (always ok)

Too many weird possibilities for unexpected key-value associations.
d.setitems() might be safer, but see d.items[i:j] below (without eliminating 
d.items() ;-)

The implication above is that OrderedDict takes an *args argument,
but really it takes a single argument that is a sequence of k,v pairs,
(and maybe some keyword options).


(Or maybe better set_keys in analogy to has_key?)

I hesitate making keys and values managed properties, because this would 
conflict with them being methods in ordinary dicts. Ordered dicts should 
resemble ordinary dicts as closely as possible. And giving it a 
different name like sequence I find confusing and unintuitive.

A resort could be the following: If keys() is given a sequence as 
argument, then use this as the new sequence of keys, and similar with 
values(). This way, no new methods need to be introduced.

You could make keys, values, and items custom descriptors which would define 
__call__
for the old key() etc accesses, well as __getitem__ and __setitem__. Then you 
could write

d.items[0], d.items[-1] = d.items[-1], d.items[0]

to swap the order of the first and last items in the thing (I hesitate to say 
dict ;-)
You could also operate on slices. BTW, before I showed an example where d[2:3] 
returned
a new dict instance rather than d.items()[:]. I think the items list is better, 
since
they naturally add, sort, reverse, etc as lists, and you can write 
OrderedDict(d[2:3]+d[1:2])
if you want a new dict.

A slice assignment to d[i:j] is really sugar for something, but we have to 
decide exactly
what in case of duplicate keys in the incoming items, either with each other 
(effictively
a shorter incoming list with the last key:value pairs replacing prior pairs 
with the same key,
but the first key determining placement -- but where? what if a key doesn't 
exists outside of
the target slice (hence not within the eliminated slice, since the whole target 
dict item list
has unique keys)? One way to define it would be
d.items[i:j] = itemseq

to be implemented as sugar for
newitems = d.items[:i] + list(itemseq) + d.items[j:]
d.clear()
d.update(newitems)
so
d.reverse()
could be spelled
d.items[:] = d.items[::-1]

If you are using slices, you can safely use them directly in the __getitem__ of 
th dict interface,
as I did in the Que mas? post. So we don't have to write d.items[i:j] and 
could write d[i:j].
The thing is, d[i:j] will tempt to skip .items in d.items[i] and write d[i], 
which has the dict key meaning,
not the item list index. It is faster not have a descriptor between though.

I think maybe allowing write to keys or values is pretty iffy. There are too 
many weird
re-associations of keys and values possible, and which you could do my other 
means if you
really really wanted to. But I do think full index and slice read access would 
be fine.

I think also that d1==d2 should effectively be implemented as d1[:] == d2[:] -- 
i.e, compare
the item lists to implement comparisons.

Detailed requirements are most of the work ;-)
I'm thinking now to try subclassing list in a constrained way instead of dict, 
but well see.

Regards,
Bengt Richter
-- 
http://mail.python.org/mailman/listinfo/python-list


Re: Why are there no ordered dictionaries?

2005-11-24 Thread Christoph Zwerschke
Fuzzyman schrieb:

 I'm going to add some of the sequence methods. I'm *not* going to allow
 indexing, but I will allow slicing.
 
 You can also do d[d.keys()[i]]
 
 This provides two ways of fetching values by index, so I don't want to
 add another.

And this would be probably faster than d.values()[i] in the usual 
implementation where values() has to be built first as Carsten noted.

-- Chris
-- 
http://mail.python.org/mailman/listinfo/python-list


Re: Why are there no ordered dictionaries?

2005-11-24 Thread Fuzzyman
d.keys() will still return a copy of the list, so d.keys()[i] will
still be slower than d.sequence[i]

Slicing shouldn't be too much slower though.

All the best,

Fuzzyman
http://www.voidspace.org.uk/python/index.shtml

-- 
http://mail.python.org/mailman/listinfo/python-list


Re: Why are there no ordered dictionaries?

2005-11-24 Thread Fuzzyman
Bengt Richter wrote:
 On Wed, 23 Nov 2005 23:00:29 +0100, Christoph Zwerschke [EMAIL PROTECTED] 
 wrote:

[snip..]
 I think also that d1==d2 should effectively be implemented as d1[:] == d2[:] 
 -- i.e, compare
 the item lists to implement comparisons.


IIUC then the odict effectively already does this.

All the best,

Fuzzyman
http://www.voidspace.org.uk/python/index.shtml

 Detailed requirements are most of the work ;-)
 I'm thinking now to try subclassing list in a constrained way instead of 
 dict, but well see.
 
 Regards,
 Bengt Richter

-- 
http://mail.python.org/mailman/listinfo/python-list


Re: Why are there no ordered dictionaries?

2005-11-24 Thread Christoph Zwerschke
Fuzzyman wrote:

 You will be able to mutate the the keys list through :
 
 d1 = OrderedDict(some_sequence_of_items)
 keys = d1.keys()
 keys.sort() # or other mutation
 d1.keys(keys)
 
 Admittedly this is a lot slower than :
 
 d1 = OrderedDict(some_sequence_of_items)
 d1.sequence.sort()
 
 *but* it frees the squence attribute from any implementation details.

You should also implement

d1.sort() or d1.sortkeys()

which will have no performance drawbacks.

-- Christoph
-- 
http://mail.python.org/mailman/listinfo/python-list


Re: Why are there no ordered dictionaries?

2005-11-24 Thread Christoph Zwerschke
Bengt Richter schrieb:

d.setvalues((13, 14)) == d = OrderedDict((1, 13), (2, 14))

 The implication above is that OrderedDict takes an *args argument,
 but really it takes a single argument that is a sequence of k,v pairs,
 (and maybe some keyword options).

Right. Interpret it as a short notation only, I did not want to change 
the interface. I think it's a common mistake to forget the brackets 
because you think one pair should be enough. At least I often forget it.

 You could make keys, values, and items custom descriptors which would define 
 __call__
 for the old key() etc accesses, well as __getitem__ and __setitem__. Then you 
 could write
 
 d.items[0], d.items[-1] = d.items[-1], d.items[0]
 
 to swap the order of the first and last items in the thing (I hesitate to say 
 dict ;-)
 You could also operate on slices.

Nice. You could also get the i-th value with d.values[i].

But is this considered good style or would it be considered dirty to 
have a callable member that also supports indexing and slicing? (I don't 
know, just asking?) Plus, it opens a can of worms by increasing the 
complexity tremendously. Let's see whether this can be handled.

 BTW, before I showed an example where d[2:3] returned
 a new dict instance rather than d.items()[:]. I think the items list
  is better, since they naturally add, sort, reverse, etc as lists,
  and you can write OrderedDict(d[2:3]+d[1:2]) if you want a new dict.

Not sure about that. I would rather expect that if you slice an object, 
you get an object of the same type. And you can also add, sort, reverse, 
etc the ordered dict if you want.

 A slice assignment to d[i:j] is really sugar for something, but we have to 
 decide exactly
 what in case of duplicate keys in the incoming items, either with each other 
 ...

You mean slice assignments to d.items[i:j]. If you make the slice 
assignment to d[i:j] then at least you cannot have conflicts in the 
incoming items. The first question is: Should a slice assignment be 
treated as deletion with subsequential addition (changing the order) or 
as a replacement (i.e. try to not change the order)? I agree that the 
second would be the expected semantics, but as you mentioned more 
difficult to implement.

  One way to define it would be
  d.items[i:j] = itemseq
 
 to be implemented as sugar for
 newitems = d.items[:i] + list(itemseq) + d.items[j:]
 d.clear()
 d.update(newitems)

Which should be the same as
d = OrderedDict(d.items[:i] + list(itemseq) + d.items[j:])
Sounds reasonable.

 So
 d.reverse()
 could be spelled
 d.items[:] = d.items[::-1]

Slice assignment for keys and values would also allow to set a new key 
order with

d.keys[:] = newkeyseq

So no need to define a setkeys() method or let keys() take arguments.
If we want to allow this kind of things at all.

 If you are using slices, you can safely use them directly in the __getitem__ 
 of th dict interface,
 as I did in the Que mas? post. So we don't have to write d.items[i:j] and 
 could write d[i:j].
 The thing is, d[i:j] will tempt to skip .items in d.items[i] and write 
 d[i], which has the dict
  key meaning, not the item list index. It is faster not have a 
descriptor between though.

I still think d[i:j] should return an ordered dict, not an item list.

 I think maybe allowing write to keys or values is pretty iffy. There are too 
 many weird
 re-associations of keys and values possible, and which you could do my other 
 means if you
 really really wanted to. But I do think full index and slice read access 
 would be fine.

There are different opinions. Fuzzyman would probably say Don't trust 
yourself? I myself am undecided. Perhaps you could expect that somebody 
knows what he does if he makes a slice assignment to d.keys. In any way, 
such an assignment should not break the directory (with broken I 
mean that the internal keys sequence does not match the keys of the 
internal dictionary). If anything does not match, it should raise a 
KeyException. If it is implemented that way, I think we can allow it.

 I think also that d1==d2 should effectively be implemented as d1[:] == d2[:] 
 -- i.e, compare
 the item lists to implement comparisons.

Wouldn't it be more performant to compare for 
d1.internal_dict==d2.internal_dict and 
d1.internal_sequence==d2.internal_sequence?
You don't keep track of the item lists, they need to be built on every 
occasion.

-- Christoph
-- 
http://mail.python.org/mailman/listinfo/python-list


Re: Why are there no ordered dictionaries?

2005-11-24 Thread Christoph Zwerschke
Fuzzyman schrieb:
 d.keys() will still return a copy of the list, so d.keys()[i] will
 still be slower than d.sequence[i]

Right, I forgot that.  Bengt suggested to implement __call__ as well as 
__getitem__ and __setitem__ for keys, values and items.

In this case, you could very effectively access it as d.values[i].

-- Christoph
-- 
http://mail.python.org/mailman/listinfo/python-list


Re: Why are there no ordered dictionaries?

2005-11-24 Thread dcalvelo
hacer probablemente.

DCA.

Piet van Oostrum wrote:
  Christoph Zwerschke [EMAIL PROTECTED] (CZ) escribió:

 CZ Eso es exactamente lo que yo queria haber!

 ¿Haber? ¿Tener? :=(
 --
 Piet van Oostrum [EMAIL PROTECTED]
 URL: http://www.cs.uu.nl/~piet [PGP 8DAE142BE17999C4]
 Private email: [EMAIL PROTECTED]

-- 
http://mail.python.org/mailman/listinfo/python-list


Re: Why are there no ordered dictionaries?

2005-11-23 Thread Steve Holden
Christoph Zwerschke wrote:
 This is probably a FAQ, but I dare to ask it nevertheless since I 
 haven't found a satisfying answer yet: Why isn't there an ordered 
 dictionary class at least in the standard list? Time and again I am 
 missing that feature. Maybe there is something wrong with my programming 
 style, but I rather think it is generally useful.
 
 I fully agree with the following posting where somebody complains why so 
 very basic and useful things are not part of the standard library:
 http://groups.google.com/group/comp.lang.python/msg/e652d2f771a49857
 
 Are there plans to get it into the standard lib sometime?
 
We're always encouraging new posters to use good subject lines. 
Several hundred posts after your original question I think everyone can 
agree that this was a *very* good subject line :-)

Perhaps now the answer top your question is more obvious: there is by no 
means universal agreement on what an ordered dictionary should do. 
Given the ease with which Python allows you to implement your chosen 
functionality it would be presumptuous of the core developers to favour 
any one of the several reasonable alternatives that might be chosen.

regards
  Steve
-- 
Steve Holden   +44 150 684 7255  +1 800 494 3119
Holden Web LLC www.holdenweb.com
PyCon TX 2006  www.python.org/pycon/

-- 
http://mail.python.org/mailman/listinfo/python-list


Re: Why are there no ordered dictionaries?

2005-11-23 Thread Fuzzyman

Christoph Zwerschke wrote:
 I still believe that the concept of an ordered dictionary (behave
 like dict, only keep the order of the keys) is intuitive and doesn't
 give you so much scope for ambiguity. But probably I need to work on an
 implementation to become more clear about possible hidden subtleties.

 Bengt Richter schrieb:

  Does that mean that the Larosa/Foord odict.py implementation in PyPI
  does not do what you want?

 Basically, it is what I had in mind. But I'm now seeing some things that
 could be improved/supplemented, e.g.
 - performance improvements

Implementation changes to follow, based on suggestions in this thread.
For *optimal* performance it needs to be implemented in C of course.
:-)

As F points out, a list of tuples may give you a data structure that
can be accessed quicker (although some operations will be slower). An
ordered dictionary will be a lot easier to use and make your code more
readable though.

 - the internal keys list should be hidden

I disagree. It is exposed so that you can manually change the order
(e.g. to create a sorted dict, rather than one ordered by key
insertion).

What do you *gain* by hiding it ?

 - list methods should be mixed in instead


Hmm... I did consider this. Which list methods would you consider
appropriate ?

The difficulty is that integers are valid keys for a dictionary.
Perhaps a subclass that uses integers as indexes instead...

You can always perform list operations on the ``sequence`` attribute of
course.

All the best,

Fuzzyman
http://www.voidspace.org.uk/python/index.shtml

 -- Christoph

-- 
http://mail.python.org/mailman/listinfo/python-list


Re: Why are there no ordered dictionaries?

2005-11-23 Thread Fuzzyman

Bengt Richter wrote:
 On 22 Nov 2005 02:16:22 -0800, Fuzzyman [EMAIL PROTECTED] wrote:

 
 Kay Schluehr wrote:
  Christoph Zwerschke wrote:
 
   That would be also biased (in favour of Python) by the fact that
   probably very little people would look for and use the package in the
   cheese shop if they were looking for ordered dicts.
 
  Does anyone actually use this site? While the Vaults offered a nice
  place and a nice interface the Cheese Shop has the appeal of a code
  slum.
 
 
 Hmmm.. it's *the* repository for Python code. I expect quite a few
 people use it...
 
 :-)
 
 I hadn't realized how much stuff was there. I generally google for stuff,
 but I will be looking directly now.

 BTW, I made a mod[1] to your odict that I think/hope is going to be generally 
 faster.
 It requires 2.4 though. It passes the same doctest, so its probably close to 
 the same.
 It stores the ordering info differently, but is also a dict subclass.


odict maintains compatibility with Python 2.2 - so it's not a change
we'd put back into the module I don't think.

Changes that keep compatibility are very welcoemd though.

 Do you happen to have a timing test that exercises various aspects, so I can 
 try it
 before I embarrass myself? Otherwise I guess I'll write something.


The only tests we have are the ones in the module.

If you create some timing tests we'd be interested in having access to
them though. They would be a useful addition.

All the best,

Fuzzyman
http://www.voidspace.org.uk/python/index.shtml

 Would the would-be users chime in with some idea of what kinds of operations 
 are
 most important timing-wise? Which would get the most use? How dynamic would 
 ordering typically be?

 [1] fairly pervasive little mods actually
 [ 9:15] C:\pywk\clpdiffodict.py odictb.py |wc
 146458   4948

 [ 9:15] C:\pywk\clpwc odict*.py
 467   1228  12483   odict.py
 511   1500  14728   odictb.py
 978   2728  27211   Totals
 
 Regards,
 Bengt Richter

-- 
http://mail.python.org/mailman/listinfo/python-list


Re: Why are there no ordered dictionaries?

2005-11-23 Thread [EMAIL PROTECTED]

Steve Holden wrote:
 Perhaps now the answer top your question is more obvious: there is by no
 means universal agreement on what an ordered dictionary should do.
 Given the ease with which Python allows you to implement your chosen
 functionality it would be presumptuous of the core developers to favour
 any one of the several reasonable alternatives that might be chosen.

It seems to be though as ordered dictionary are slowly to be confined
to only ordered on order of change to the dictionary.

-- 
http://mail.python.org/mailman/listinfo/python-list


Re: Why are there no ordered dictionaries?

2005-11-23 Thread Fuzzyman

Christoph Zwerschke wrote:
 One implementation detail that I think needs further consideration is in
 which way to expose the keys and to mix in list methods for ordered
 dictionaries.

 In http://aspn.activestate.com/ASPN/Cookbook/Python/Recipe/107747
 the keys are exposed via the keys() method which is bad. It should be a
 copy only, like for ordinary dicts (one comment also mentions that).

 In Foord/Larosa's odict, the keys are exposed as a public member which
 also seems to be a bad idea (If you alter the sequence list so that it
 no longer reflects the contents of the dictionary, you have broken your
 OrderedDict).


So don't do it. ;-)

 I think it would be probably the best to hide the keys list from the
 public, but to provide list methods for reordering them (sorting,
 slicing etc.).

 For instance:

 d1 = OrderedDict( (1, 11), (2, 12), 3, 13) )

 d1[1:] == OrderedDict( (2, 12), 3, 13) )


So what do you want returned when you ask for d1[1] ? The member keyed
by 1, or the item in position 1 ?

You can access the members using list operations on the sequence
attribute.

E.g. d1[d1.sequence[index]]

This could probably be made more convenient.

 d1[0] + d1[2] == OrderedDict( (1, 11), (3, 13) )

 d1.reverse() == OrderedDict( (3, 13), (2, 12), 1, 11) )


Interesting idea.

 d1.insert(1, (4, 14))
  == OrderedDict( (1, 11), (4, 14), (2, 12), 3, 13) )


Also an interesting idea.

 etc.

 But no other way to directly manipulate the keys should be provided.


Why - don't trust yourself with it ?

All the best,

Fuzzyman
http://www.voidspace.org.uk/python/index.shtml

 -- Christoph

-- 
http://mail.python.org/mailman/listinfo/python-list


Re: Why are there no ordered dictionaries?

2005-11-23 Thread Fuzzyman
There is already an update method of course. :-)

Slicing an ordered dictionary is interesting - but how many people are
actually going to use it ? (What's your use case)

You can already slice the sequence atribute and iterate over that.

All the best,


Fuzzyman
http://www.voidspace.org.uk/python/index.shtml

-- 
http://mail.python.org/mailman/listinfo/python-list


Re: Why are there no ordered dictionaries?

2005-11-23 Thread Fuzzyman
While we're on the subject, it would be useful to be able to paste in a
changelog as well as a description.

Currently when updating versions you have to include the changelog in
the description - or not at all...

All the best,

Fuzzyman
http://www.voidspace.org.uk/python/index.shtml

-- 
http://mail.python.org/mailman/listinfo/python-list


Re: Why are there no ordered dictionaries?

2005-11-23 Thread Kay Schluehr

[EMAIL PROTECTED] wrote:
 Steve Holden wrote:
  Perhaps now the answer top your question is more obvious: there is by no
  means universal agreement on what an ordered dictionary should do.
  Given the ease with which Python allows you to implement your chosen
  functionality it would be presumptuous of the core developers to favour
  any one of the several reasonable alternatives that might be chosen.
 
 It seems to be though as ordered dictionary are slowly to be confined
 to only ordered on order of change to the dictionary.

While I'm only +0 for a standard odict I'm wondering that discussing
this topic leads to the auctoritative conclusion that it is unsolvable,
we have to accept infinite diversity etc. where people like me seeing a
classification immediately ( mathematical education? ) . Of course this
matter is trivial but we already know about monster-threads revolving
around decorator syntax ( including hurt souls and semi-scientific
papers ) and abandoning the print statement in Python 3.0.

-- 
http://mail.python.org/mailman/listinfo/python-list


Re: Why are there no ordered dictionaries?

2005-11-23 Thread Duncan Booth
Christoph Zwerschke wrote:

 Ok, I just did a little research an compared support for ordered dicts 
 in some other languages:
 
Just to add to your list:

In Javascript Object properties (often used as an associative array) are 
defined as unordered although as IE seems to always store them in the order 
of original insertion it wouldn't surprise me if there are a lot of 
websites depending on that behaviour.

Javascript Array indexes are also stored as properties and are therefore 
also unordered.
-- 
http://mail.python.org/mailman/listinfo/python-list


Re: Why are there no ordered dictionaries?

2005-11-23 Thread Bengt Richter
On 23 Nov 2005 01:24:46 -0800, Kay Schluehr [EMAIL PROTECTED] wrote:


[EMAIL PROTECTED] wrote:
 Steve Holden wrote:
  Perhaps now the answer top your question is more obvious: there is by no
  means universal agreement on what an ordered dictionary should do.
  Given the ease with which Python allows you to implement your chosen
  functionality it would be presumptuous of the core developers to favour
  any one of the several reasonable alternatives that might be chosen.
 
 It seems to be though as ordered dictionary are slowly to be confined
 to only ordered on order of change to the dictionary.

While I'm only +0 for a standard odict I'm wondering that discussing
this topic leads to the auctoritative conclusion that it is unsolvable,
we have to accept infinite diversity etc. where people like me seeing a
classification immediately ( mathematical education? ) . Of course this
matter is trivial but we already know about monster-threads revolving
around decorator syntax ( including hurt souls and semi-scientific
papers ) and abandoning the print statement in Python 3.0.

I think the concept has converged to a replace-or-append-by-key ordering
of key:value items with methods approximately like a dict. We're now
into usability aspects such as syntactic sugar vs essential primitives,
and default behaviour vs selectable modes, ISTM.

E.g., it might be nice to have a mode that assumes d[key] is d.items()[k][1] 
when
key is an integer, and otherwise uses dict lookup, for cases where the use
case is just string dict keys.

But feature creep is sure a threat to clean design.

Regards,
Bengt Richter
-- 
http://mail.python.org/mailman/listinfo/python-list


Re: Why are there no ordered dictionaries?

2005-11-23 Thread Rick Wotnaz
Fuzzyman [EMAIL PROTECTED] wrote in
news:[EMAIL PROTECTED]: 

 
 Christoph Zwerschke wrote:
 - the internal keys list should be hidden
 
 I disagree. It is exposed so that you can manually change the
 order (e.g. to create a sorted dict, rather than one ordered
 by key insertion).
 
 What do you *gain* by hiding it ?

The internal list should be 'hidden' in the sense that it itself 
would not be modifiable, though it should be routine to obtain a 
copy of it at any time. That copy could then be arranged as needed. 
Any rearrangement of the original list's order destroys the reason 
for having an entry- or change-ordered dict in the first place.

-- 
rzed
-- 
http://mail.python.org/mailman/listinfo/python-list


Re: Why are there no ordered dictionaries?

2005-11-23 Thread Magnus Lycka
Ganesan Rajagopal wrote:
 [EMAIL PROTECTED] com [EMAIL PROTECTED] writes:   what would be 
 
 the definition of sorted and ordered, before we can  go on ? Sorted 
 would be ordered by key comparison. Iterating over such a container will 
 give you the keys in sorted order. Java calls this a SortedMap. See 
 http://java.sun.com/j2se/1.4.2/docs/api/java/util/SortedMap.html C++ STL 
 map container is also a Sorted Associative container. See 
 http://www.sgi.com/tech/stl/Map.html  Ganesan

In Python it's simple to keep a list sorted using bisect.insort.

  import bisect
  l=[]
  bisect.insort(l,4)
  bisect.insort(l,3)
  bisect.insort(l,5)
  bisect.insort(l,1)
  bisect.insort(l,6)
  bisect.insort(l,2)
  l
[1, 2, 3, 4, 5, 6]

Assuming a list with n tuples, where the first m elements in each
tuple is the key, we can also fetch elements through keys (interval
matches as well as exact matches) with O(log n) performance.

I guess those who thinks this isn't enough should push for placing
something like Zope's BTree classes in the standard library.

Fredrik already showed how simple and cheap it was to make a dict out
of a list. I think this is a superior solution to odicts as suggested,
but by all means, if people want odicts, make sure that there is a
good implementation available, use it, show that it's useful to
others, and maybe, some time in the future, it will be considered
for inclusion in the standard library.
-- 
http://mail.python.org/mailman/listinfo/python-list


Re: Why are there no ordered dictionaries?

2005-11-23 Thread Carsten Haese
On Tue, 2005-11-22 at 20:44, Tom Anderson wrote:
 On Tue, 22 Nov 2005, Carsten Haese wrote:
 
  On Tue, 2005-11-22 at 14:37, Christoph Zwerschke wrote:
 
  In Foord/Larosa's odict, the keys are exposed as a public member which 
  also seems to be a bad idea (If you alter the sequence list so that it 
  no longer reflects the contents of the dictionary, you have broken your 
  OrderedDict).
 
  That could easily be fixed by making the sequence a managed property 
  whose setter raises a ValueError if you try to set it to something 
  that's not a permutation of what it was.
 
 I'm not a managed property expert (although there's a lovely studio in 
 Bayswater you might be interested in), but how does this stop you doing:
 
 my_odict.sequence[0] = Shrubbery()

It would only break if the getter returns the internal list directly.
The getter should return a copy instead, which is what the keys() method
already does anyway. This would ensure that the only way to alter the
sequence is by replacing it in its entirety.

-Carsten.


-- 
http://mail.python.org/mailman/listinfo/python-list


Re: Why are there no ordered dictionaries?

2005-11-23 Thread Fuzzyman

Rick Wotnaz wrote:
 Fuzzyman [EMAIL PROTECTED] wrote in
 news:[EMAIL PROTECTED]:

 
  Christoph Zwerschke wrote:
  - the internal keys list should be hidden
 
  I disagree. It is exposed so that you can manually change the
  order (e.g. to create a sorted dict, rather than one ordered
  by key insertion).
 
  What do you *gain* by hiding it ?

 The internal list should be 'hidden' in the sense that it itself
 would not be modifiable, though it should be routine to obtain a
 copy of it at any time. That copy could then be arranged as needed.
 Any rearrangement of the original list's order destroys the reason
 for having an entry- or change-ordered dict in the first place.


That's not the only use case. Other use cases are to have a specific
order, not based on entry time.

Simple example :

d1 = OrderedDict(some_dict.items())
d1.sequence.sort()

d1 is now an ordered dict with the keys in alphabetic order.

If you don't want to modify sequence, don't. If you want a copy do :

seq = d1.sequence[:]

All the best,

Fuzzyman
http://www.voidspace.org.uk/python/index.shtml

 -- 
 rzed

-- 
http://mail.python.org/mailman/listinfo/python-list


Re: Why are there no ordered dictionaries?

2005-11-23 Thread Alex Martelli
Fuzzyman [EMAIL PROTECTED] wrote:
   ...
  - the internal keys list should be hidden
 
 I disagree. It is exposed so that you can manually change the order
 (e.g. to create a sorted dict, rather than one ordered by key
 insertion).
 
 What do you *gain* by hiding it ?

Freedom of implementation, of course.  E.g., I can perhaps get better
performance by keeping a red-black tree of (insertiontime,key) pairs, so
for example deleting a key is O(log(N)) rather than O(N) as it would
have to be if the sequence had to be kept as a Python list.

What ELSE do you ever gain by enforcing abstraction and information
hiding?  Conceptual integrity and implementation freedom...


  - list methods should be mixed in instead
 
 Hmm... I did consider this. Which list methods would you consider
 appropriate ?
 
 The difficulty is that integers are valid keys for a dictionary.
 Perhaps a subclass that uses integers as indexes instead...

What about allowing slicing, taking advantage of the fact that slices
are NOT valid dictionary keys?
Presumably sort and reverse methods are also desired.

 You can always perform list operations on the ``sequence`` attribute of
 course.

But NOT having to expose .sequence as a real mutable list whose changes
affect ordering has many advantages, as above noticed.


Alex
-- 
http://mail.python.org/mailman/listinfo/python-list


Re: Why are there no ordered dictionaries?

2005-11-23 Thread Alex Martelli
Fuzzyman [EMAIL PROTECTED] wrote:

 There is already an update method of course. :-)
 
 Slicing an ordered dictionary is interesting - but how many people are
 actually going to use it ? (What's your use case)

I detest and abhor almost-sequences which can't be sliced (I consider
that a defect of collections.deque).  If the ordered dictionary records
by its sequencing the time order of key insertion, being able to ask for
the last 5 keys entered or the first 3 keys entered seem to me to be
perfectly natural use cases, and most naturally accomplished by slicing
of course, d[-5:] and d[:3] respectively.


Alex
-- 
http://mail.python.org/mailman/listinfo/python-list


Re: Why are there no ordered dictionaries?

2005-11-23 Thread Christoph Zwerschke
Steve Holden schrieb:
 Perhaps now the answer top your question is more obvious: there is by no 
 means universal agreement on what an ordered dictionary should do. 
 Given the ease with which Python allows you to implement your chosen 
 functionality it would be presumptuous of the core developers to favour 
 any one of the several reasonable alternatives that might be chosen.

The discussion showed indeed that there are some points which are not so 
straightforward as I believed. But I still don't see the several 
reasonable alternatives. So far all implementations I have seen are 
basically pretty similar. Is there any implementation that is basically 
different from Foord/Larosa's odict? I still don't see a principal 
problem here, just the problem that the existing implementations are not 
well enough thought-out and sophisticated enough.

  Given the ease with which Python allows you to implement your chosen
  functionality it would be presumptuous of the core developers to
  favour any one of the several reasonable alternatives that might be
  chosen.

You could say the same about the idea of sets in Python, and it is 
probably the reason why it took so much time until they became a part of 
Python. I wished that had happened earlier, since sets are the basic 
mathematic structure. I'm now very happy to have sets not only in the 
standard lib but even as built-in types and I'm sure there hasn't been 
universal agreement on how sets should be implemented either. I don't 
think it was presumptuous to finally settle down on one implementation.

Of course, ordered dictionaries are no candidates for becoming built-in 
data types, and the existing implementations are not sophisticated and 
mature enough to go to the standard lib right now. But principally, if 
an improved version is developed (maybe on the occasion of this thread) 
and will be tested and proven, why should it not go to the standard lib 
some day?

BTW, somebody has suggested it could go to collections which sounds 
like the right place, but the description says the module is intended 
for High-performance container datatypes, and, as has been discussed, 
ordered dictionaries are not used for performance or efficiency reasons, 
but rather for reasons of convenience. So *if* they ever go to the 
standard lib, I'm not sure whether collections would be the right 
place. Or collections will need a different description - maybe there 
are other interesting basic collection types which are chosen for 
convenience, not for performance (for instance, ordered sets)?

-- Christoph

-- 
http://mail.python.org/mailman/listinfo/python-list


Re: Why are there no ordered dictionaries?

2005-11-23 Thread Christoph Zwerschke
[EMAIL PROTECTED] schrieb:
 It seems to be though as ordered dictionary are slowly to be confined
 to only ordered on order of change to the dictionary.

Ordered dictionary means that the keys are not an ordinary set like in 
an ordinary dictionary, but an ordered set. I think this definition is 
pretty straightforward and common. An ordered set is the same as a 
unique list, i.e. a list where all elements are unique.

When there is automatical ordering using a comparison function, I would 
not speak of an ordered directory, but of a sorted directory. This 
would be basically a dictionary plus a comparison function. The keys 
would always be iterated in the order given by the comparison function. 
It would be nice to have a sorted dictionary as well, even if you can 
achieve the same by calling the sorted built-in on the keys. Think of a 
sorted directory as a subclass of ordered directories. Implementing it 
that way would even have perfomance benefits if the keys are inserted 
using the bisect algorithm. This is better than calling sorted() on the 
keys of an ordinary dictionary many times.

By the way, you will find the same terminology in Smalltalk, where 
SortedCollection is a subclass of OrderedCollection.

-- Christoph
-- 
http://mail.python.org/mailman/listinfo/python-list


Re: Why are there no ordered dictionaries?

2005-11-23 Thread Christoph Zwerschke
Bengt Richter wrote:
  I think the concept has converged to a replace-or-append-by-key ordering
  of key:value items with methods approximately like a dict. We're now
  into usability aspects such as syntactic sugar vs essential primitives,
  and default behaviour vs selectable modes, ISTM.

Yes, and we would be good if we do not stop the discussion at this point 
with nothing, but really create such a sophisticated implementation. 
Whether it will become popular or go to the standard lib some day is a 
completely different question.

  E.g., it might be nice to have a mode that assumes d[key] is 
d.items()[k][1] when
  key is an integer, and otherwise uses dict lookup, for cases where 
the use
  case is just string dict keys.

I also thought about that and I think PHP has that feature, but it's 
probably better to withstand the temptation to do that. It could lead to 
an awful confusion if the keys are integers.

-- Christoph
-- 
http://mail.python.org/mailman/listinfo/python-list


Re: Why are there no ordered dictionaries?

2005-11-23 Thread Christoph Zwerschke
* C++ has a Map template in the STL which is ordered (a Sorted 
Associative Container).

Alex Martelli wrote:

 Ordered *by comparisons on keys*, NOT by order of insertion -- an
 utterly and completely different idea.

Shame on me. I talked so much about the difference between ordered and 
sorted and now I wrote such a confusing sentence. You're right, C++ 
Maps are not an example for ordered dictionaries, but for sorted 
dictionaries.

-- Christoph
-- 
http://mail.python.org/mailman/listinfo/python-list


Re: Why are there no ordered dictionaries?

2005-11-23 Thread Christoph Zwerschke
Duncan Booth schrieb:
 In Javascript Object properties (often used as an associative array) are 
 defined as unordered although as IE seems to always store them in the order 
 of original insertion it wouldn't surprise me if there are a lot of 
 websites depending on that behaviour.

You're right with both. The ECMA language definition says object 
properties are an unordered collection, but MSIE and probably other 
browsers keep the order in which they were created. Of course one should 
not rely on that.

-- Christoph
-- 
http://mail.python.org/mailman/listinfo/python-list


Re: Why are there no ordered dictionaries?

2005-11-23 Thread Carsten Haese
On Wed, 2005-11-23 at 15:17, Christoph Zwerschke wrote:
 Bengt Richter wrote:
   I think the concept has converged to a replace-or-append-by-key ordering
   of key:value items with methods approximately like a dict. We're now
   into usability aspects such as syntactic sugar vs essential primitives,
   and default behaviour vs selectable modes, ISTM.
 
 Yes, and we would be good if we do not stop the discussion at this point 
 with nothing, but really create such a sophisticated implementation. 
 Whether it will become popular or go to the standard lib some day is a 
 completely different question.
 
   E.g., it might be nice to have a mode that assumes d[key] is 
 d.items()[k][1] when
   key is an integer, and otherwise uses dict lookup, for cases where 
 the use
   case is just string dict keys.
 
 I also thought about that and I think PHP has that feature, but it's 
 probably better to withstand the temptation to do that. It could lead to 
 an awful confusion if the keys are integers.

Thus quoth the Zen of Python:
Explicit is better than implicit.
In the face of ambiguity, refuse the temptation to guess.

With those in mind, since an odict behaves mostly like a dictionary, []
should always refer to keys. An odict implementation that wants to allow
access by numeric index should provide explicitly named methods for that
purpose.

-Carsten


-- 
http://mail.python.org/mailman/listinfo/python-list


Re: Why are there no ordered dictionaries?

2005-11-23 Thread Christoph Zwerschke
Alex Martelli wrote:

 However, since Christoph himself just misclassified C++'s std::map as
 ordered (it would be sorted in this new terminology he's now
 introducing), it seems obvious that the terminological confusion is
 rife.  Many requests and offers in the past for ordered dictionaries
 (e.g. on this group) were also sorted, NOT ordered, in this new
 terminology.

I'm sorry again. Please don't conclude that others are as uneducated as 
I am (I haven't studied computer science but mathematics). Speaking 
about ordered and sorted in the context of collections is not a new 
terminology I am introducing, but seems to be pretty common in computer 
science (see, e.g. 
http://www.gamespp.com/java/dataStructuresInJavaPart6.html).

Perhaps Pythonists are not used to that terminology, since they use the 
term list for an ordered collection. An ordered dictionary is a 
dictionary whose keys are a (unique) list. Sometimes it is also called a 
sequence (therefore in the odict implementation, the keys attribute 
has this name). A unique list, in turn, can also be called an ordered 
set, so you can also understand an ordered dictionary as a dictionary 
whose keys are an ordered set. I think all of this is pretty logical ;-)

-- Christoph
-- 
http://mail.python.org/mailman/listinfo/python-list


Re: Why are there no ordered dictionaries?

2005-11-23 Thread Christoph Zwerschke
Ganesan Rajagopal wrote:

 the definition of sorted and ordered, before we can  go on ? Sorted 
 would be ordered by key comparison. Iterating over such a container will 
 give you the keys in sorted order. Java calls this a SortedMap. See 
 http://java.sun.com/j2se/1.4.2/docs/api/java/util/SortedMap.html C++ STL 
 map container is also a Sorted Associative container. See 
 http://www.sgi.com/tech/stl/Map.html  Ganesan

Exactly, that's sorted. Ordered means the same there is some order 
between the existing elements, but there is no magic (i.e. a general 
comparison function) for ordering new elements. Thus, if you add an 
element to an ordered collection, it simply gets appended (is considered 
as the greatest of all elements) by convention, whereas if you add an 
element to a sorted collection, it will be inserted into the correct 
place by using the comparison function.

-- Christoph
-- 
http://mail.python.org/mailman/listinfo/python-list


Re: Why are there no ordered dictionaries?

2005-11-23 Thread Christoph Zwerschke
Alex Martelli schrieb:

 I detest and abhor almost-sequences which can't be sliced (I consider
 that a defect of collections.deque).  If the ordered dictionary records
 by its sequencing the time order of key insertion, being able to ask for
 the last 5 keys entered or the first 3 keys entered seem to me to be
 perfectly natural use cases, and most naturally accomplished by slicing
 of course, d[-5:] and d[:3] respectively.

I agree. A use case was requested: Say your dictionary holds form 
fields, and you know the last field is always a hidden field you wont to 
ignore in your output, or your dictionary holds attributes of a 
database, and you don't want to print the first attribute which is 
always some kind of uninteresting OID, then you would write
for field in d[1:] or for field in d[:-1].

(Otherwise, you would have to write for field in d.keys()[1:] etc.)

-- Christoph
-- 
http://mail.python.org/mailman/listinfo/python-list


Re: Why are there no ordered dictionaries?

2005-11-23 Thread Christoph Zwerschke
Bengt Richter wrote:

   from odictb import OrderedDict
   d1 = OrderedDict([(1, 11), (2, 12), (3, 13)])
   d1
  {1: 11, 2: 12, 3: 13}
   d1[1:]
  {2: 12, 3: 13}
   d1[0:1] + d1[2:3]
  {1: 11, 3: 13}
   d1.reverse()
   d1
  {3: 13, 2: 12, 1: 11}
   d1.insert(1, (4,14))
   d1
  {3: 13, 4: 14, 2: 12, 1: 11}
   d1.items()
  [(3, 13), (4, 14), (2, 12), (1, 11)]
   d1.keys()
  [3, 4, 2, 1]
   d1.values()
  [13, 14, 12, 11]
   d1[1:2]
  {4: 14}
   d1[-1:]
  {1: 11}
 
 Que mas?

Eso es exactamente lo que yo queria haber!

-- Chris
-- 
http://mail.python.org/mailman/listinfo/python-list


Re: Why are there no ordered dictionaries?

2005-11-23 Thread Christoph Zwerschke
 I think it would be probably the best to hide the keys list from the 
 public, but to provide list methods for reordering them (sorting, 
 slicing etc.).

Tom Anderson wrote:

 I'm not too keen on this - there is conceptually a list here, even if 
 it's one with unusual constraints, so there should be a list i can 
 manipulate in code, and which should of course be bound by those 
 constraints.

Think of it similar as the case of an ordinary dictionary: There is 
conceptually a set here (the set of keys), but you cannot manipulate it 
directly, but only through the according dictionary methods.

For an ordedred dictionary, there is conceptually a list (or more 
specifically a unique list). Again you should not manipulate it 
directly, but only through methods of the ordered dictionary.

This sounds at first more complicated, but is in reality more easy.

For instance, if I want to put the last two keys of an ordered dict d at 
the beginning, I would do it as d = d[:-2] + d[-2:].

With the list attribute (called sequence in odict, you would have to 
write: d.sequence = d.sequence[:-2] + d.sequence[-2:]. This is not only 
longer to write down, but you also have to know that the name of the 
attribute is sequence. Python's strength is that you don't have to 
keep many details in mind because it has a small basic vocabulary and 
orthogonal use. I prefer the ordered dictionary does not introduce new 
concepts or attributes if everything can be done intuitively with the 
existing Python methods and operators.

-- Christoph
-- 
http://mail.python.org/mailman/listinfo/python-list


Re: Why are there no ordered dictionaries?

2005-11-23 Thread Christoph Zwerschke
Fuzzyman wrote:

 So what do you want returned when you ask for d1[1] ? The member keyed
 by 1, or the item in position 1 ?

In case of conflict, the ordered dictionary should behave like a 
dictionary, not like a list. So d1[1] should be the member keyed by 1, 
not the item in position 1. Only in case there is no member keyed by 1, 
the item in position 1 could be returned, but I think that would be too 
adventurous a hattrick and can lead to big confusion. Better to raise a 
KeyError in that case.

 But no other way to directly manipulate the keys should be provided.

 Why - don't trust yourself with it ?

No, because I think it is not needed if list operations like insert are 
directly possible on your dictionary.

But maybe methods such as setkeys() and setvalues() would be nice to 
have in addition.

Instead of writing d.sequence = new_sequence, I would write 
d.setkeys(new_sequence). But I'm not sure what to do if new_sequence is 
not a permutation of the old one. Raise a KeyError? Or even swallow 
this? For instance

d = OrderedDict((1,11), (2,12))

d.setkeys((2, 1)) == d = OrderedDict((2, 11), (1, 12))

d.setkeys((3, 4)) == d = OrderedDict((3, 11), (4, 12)) (or KeyError?)

d.setvalues((12, 11)) == d = OrderedDict((1, 12), (2, 11))

d.setvalues((13, 14)) == d = OrderedDict((1, 13), (2, 14)) (always ok)

(Or maybe better set_keys in analogy to has_key?)

I hesitate making keys and values managed properties, because this would 
conflict with them being methods in ordinary dicts. Ordered dicts should 
resemble ordinary dicts as closely as possible. And giving it a 
different name like sequence I find confusing and unintuitive.

A resort could be the following: If keys() is given a sequence as 
argument, then use this as the new sequence of keys, and similar with 
values(). This way, no new methods need to be introduced.

-- Christoph
-- 
http://mail.python.org/mailman/listinfo/python-list


Re: Why are there no ordered dictionaries?

2005-11-23 Thread Christoph Zwerschke
Fuzzyman wrote:

- the internal keys list should be hidden

 I disagree. It is exposed so that you can manually change the order
 (e.g. to create a sorted dict, rather than one ordered by key
 insertion). What do you *gain* by hiding it ?

See my other posting. Of course hiding the list can only be done, if

- list methods be mixed in instead

In this case, you can change the order directly by using the list 
methods on the dictionary. Sorting would be an example. Instead of

d.sequence = sorted(d.sequence)

you could simply write d.sort() which does the same.

 Hmm... I did consider this. Which list methods would you consider
 appropriate ?

Everything method that does not clash with the use as dictionary. For 
instance, both lists and dicts have __getitem__ and __setitem__, so im 
this case, the dictionary method must take precedence. But a dictionary 
has not __getslice__ and __setslice__, so here the list methods can be 
used (__getslice__ is actually deprecated, but you get the idea). In 
some cases, like __delitem__, both have it, but there is no clash.

Other interesting methods are sort() and reverse().

Here, we have another problem however: There is not only the list of 
keys, but also the list of values, and sometimes, as in the case of 
sort() and reverse(), it would be also nice to have it operate on the 
list of values. How should this be done? PHP solves it by using two 
different methods ksort and asort for keys and values. In this notation:

d = OrderedDict( (1,13), (3,12), (2,11) )

d.ksort() == d = ( (1,13), (2,11), (3,12) )
d.asort() == d = ( (2,11), (3,12), (1,13) )

Similar for reverse().

If the keys() and values() methods would be extended to be setters, then 
d.ksort() = d.keys(sorted(d.keys())) and
d.asort() = d.values(sorted(d.values()))

Anyway, I don't like ksort and asort. If it must be, I'd rather use

d.ksort() = d.sortkeys()
d.asort() = d.sortvalues()

d.sort() could default to one of them (not sure which one).

-- Christoph
-- 
http://mail.python.org/mailman/listinfo/python-list


Re: Why are there no ordered dictionaries?

2005-11-23 Thread Christoph Zwerschke
Fuzzyman wrote:

 That's not the only use case. Other use cases are to have a specific
 order, not based on entry time.
 
 Simple example :
 d1 = OrderedDict(some_dict.items())
 d1.sequence.sort()
 d1 is now an ordered dict with the keys in alphabetic order.

As I said, I would not need to access the sequence, if I can write
d1.sort() or d1.sortkeys()

 If you don't want to modify sequence, don't. If you want a copy do :
 seq = d1.sequence[:]

This is not needed since you can do the same with: seq = d1.keys()

-- Christoph
-- 
http://mail.python.org/mailman/listinfo/python-list


Re: Why are there no ordered dictionaries?

2005-11-23 Thread Christoph Zwerschke
Carsten Haese schrieb:

 Thus quoth the Zen of Python:
 Explicit is better than implicit.
 In the face of ambiguity, refuse the temptation to guess.
 
 With those in mind, since an odict behaves mostly like a dictionary, []
 should always refer to keys. An odict implementation that wants to allow
 access by numeric index should provide explicitly named methods for that
 purpose.

Exactly. But I don't think in this case such methods would be needed. 
You easily get the i-th value in the ordered dict as d.values()[i].

-- Chris


-- 
http://mail.python.org/mailman/listinfo/python-list


Re: Why are there no ordered dictionaries?

2005-11-23 Thread Christoph Zwerschke
Here is another old posting I just found which again gives the same use 
cases and semantics:

http://mail.python.org/pipermail/python-dev/2005-March/051974.html

Keys are iterated over in the order that they are added. Setting a
value using a key that compares equal to one already in the dict
replaces the value, but not the key, and does not change the iteration
order. Removing a key (and value) then re-adding it moves the key to the
end of the iteration order.

So far all those who would like to have an ordered dict seem to have the 
same semantics in mind.
-- 
http://mail.python.org/mailman/listinfo/python-list


Re: Why are there no ordered dictionaries?

2005-11-23 Thread Carsten Haese
On Wed, 23 Nov 2005 23:39:22 +0100, Christoph Zwerschke wrote
 Carsten Haese schrieb:
 
  Thus quoth the Zen of Python:
  Explicit is better than implicit.
  In the face of ambiguity, refuse the temptation to guess.
  
  With those in mind, since an odict behaves mostly like a dictionary, []
  should always refer to keys. An odict implementation that wants to allow
  access by numeric index should provide explicitly named methods for that
  purpose.
 
 Exactly. But I don't think in this case such methods would be 
 needed. You easily get the i-th value in the ordered dict as 
 d.values()[i].
 
 -- Chris

True enough, but unless the odict has its list of values on hand, you're
asking the odict to build a list of all its values just so that you can get
the i'th element. Having a method that does the equivalent of d[d.sequence[i]]
would be cleaner and more efficient.

-Carsten

-- 
http://mail.python.org/mailman/listinfo/python-list


Re: Why are there no ordered dictionaries?

2005-11-23 Thread Alex Martelli
Christoph Zwerschke [EMAIL PROTECTED] wrote:
   ...
 d.ksort() = d.sortkeys()
 d.asort() = d.sortvalues()
 
 d.sort() could default to one of them (not sure which one).

Define JUST d.sort, you can trivially implement the other as
d.sort(key=d.get).


Alex
-- 
http://mail.python.org/mailman/listinfo/python-list


Re: Why are there no ordered dictionaries?

2005-11-22 Thread Fredrik Lundh
Tom Anderson wrote:

 Incidentally, can we call that the Larosa-Foord ordered mapping?

The implementation, sure.

 Then it sounds like some kind of rocket science discrete mathematics stuff

But math folks usually name things after the person(s) who came
up with the idea, not just some random implementer.  The idea of
combining unordered mappings and ordered sequences is older than
Python itself.

/F



-- 
http://mail.python.org/mailman/listinfo/python-list


Re: Why are there no ordered dictionaries?

2005-11-22 Thread Christoph Zwerschke
Alex Martelli schrieb:
 Perl hashes now keep track of 'order of keys'?  That's new to me, they
 sure didn't back when I used Perl!

Maybe I shouldn't have talked about Perl when I'm an ignoramus about 
that language... You're right, Perl has unordered arrays. That was new 
to me since I associate the term array always with ordered and I 
just remembered that PHP's assoc arrays are similar to Perl's but in 
fact, and the examples I have read did not mention about that problem.

 What about PHP?

You can conclude that PHP's assoc arrays are ordered from the fact that 
the language provides a ksort() function to order the keys. And I think 
PHP's insertion order is the one I mentioned in my last post.

Anyway, it would be interesting to examine this in detail and how this 
is implemented in other languages.

 first insertion (since the last deletion if any) is ONE unambiguous
 definition, but surely not _the_ ONE with emphasis on ``the''.
 I see nothing _ambiguous_ (nor _unnatural_) in being interested in the
  *last* insertion, for example; indeed if phrased as upon insertion, put
  the key at the end of the sequence (whether it was already elsewhere in
  the sequence of not), with no need for conditionals regarding previous
 existence, it might appear more conceptually compact.

But it would not satisfy the concept of keys of a dictionary which are 
always unique.

BTW, there are some boundary conditions that should be fulfilled for the 
insertion order, most obviously:

If you define an ordered dict that way:

d = odict()
d['a'] = 1
d['b'] = 2
d['c'] = 3

The keys should then be orderes as ('a', 'b', 'c').

 Anyway -- subclassing dict to implement your definition is reasonably
 easy, and we could put the resulting package on the Cheese Shop.  I hope
 python.org keeps good enough statistics to be able to tell us, a couple
 months later, how many people downloaded said package, vs how many
 people downloaded a complete Python distro; of course, that ratio is
 biased (in favour of the package) by the fact that many people already
 have a complete distro available, while initially nobody would have the
 package, but if we measure when things settle, after letting a month of
 two or 'transient' pass, that effect might be lessened.

That would be also biased (in favour of Python) by the fact that 
probably very little people would look for and use the package in the 
cheese shop if they were looking for ordered dicts. I for example would 
probably use ordered dicts if they were part of the standard lib, but 
not if I have to install it as an obscure separate package. So I don't 
think that will give us a real clue how many people would like ordered 
dicts in the standard lib.

But anyway, if I find some time, I will research a little bit more about 
the issue and create such a package, because it seems to me that the 
existing packages and recipes are not really satisfying and you're right 
it seems to be reasonably easy. It's on my todo list now...

-- Christoph
-- 
http://mail.python.org/mailman/listinfo/python-list


Re: Why are there no ordered dictionaries?

2005-11-22 Thread Christoph Zwerschke
Bengt Richter schrieb:
 Ok, so if not in the standard library, what is the problem? Can't find what
 you want with google and PyPI etc.? Or haven't really settled on what your
 _requirements_ are? That seems to be the primary problem people who complain
 with why no sprollificator mode? questions.

What I don't understand is why legitimate questions such as why are 
there no ordered dictionaries are immediately interpreted as 
*complaints* and not just as questions. If I ask such a question, I am 
not complaining but trying to simply figure out *why* there is no such 
thing. Probably there are reasons and all I want to know is find these 
reasons and learn a little bit more about Python in doing so.

Why can't such questions be discussed in a factual, calm and friendly way?

  They don't know what they really mean when it comes down to a DYFR
  (Define Your Felicitous Requirements) challenge.

I don't think that this was true in this case, and even if this is the 
outcome, those who asked the question will have learned something.

I think a discussion group is not there for only presenting mature, 
sophisticated thoughts and concepts, but also for thinking loud 
together with other about these issues. We all know that clarifying our 
thoughts works often best if you discuss them with others. And I think 
that's one purpose of discussion lists. Asking questions should not be 
immediately be discouraged, even silly questions. If it is really a FAQ, 
you can simply point to the FAQ or add the answer in the FAQ list if it 
is missing there.

-- Chris
-- 
http://mail.python.org/mailman/listinfo/python-list


Re: Why are there no ordered dictionaries?

2005-11-22 Thread Fredrik Lundh
Alex Martelli wrote:

 What about PHP?  Thanks!

according to some random PHP documentation I found on the intarweb:

An array in PHP is actually an ordered map. A map is a type that
maps values to keys.

and later:

A key may be either an integer or a string. If a key is the standard
representation of an integer, it will be interpreted as such (i.e. 8
will be interpreted as 8, while 08 will be interpreted as 08). Floats
in key are truncated to integer.

and later:

You cannot use arrays or objects as keys. Doing so will result in a
warning: Illegal offset type.


at which point my brain raised an exception.

/F



-- 
http://mail.python.org/mailman/listinfo/python-list


Re: Why are there no ordered dictionaries?

2005-11-22 Thread Christoph Zwerschke
Bengt Richter wrote:

  d = OrderedDict(); d[1]='one'; d[2]='two' = list(d) = [1, 2]
  ok, now we do d[1]='ein' and what is the order? list(d) = [2, 1] ??
  Or do replacements not count as insertions?

If you simply set a value for a key that already exists, the order 
should not be changed. I think this is intuitive.

  Or maybe you want to permit append and NOT prevent
  [('a',1), ('a':2)] and maybe d['a'] = [1, 2] ???

You could ask the same question about dict. I think that is not an 
option. Why should you want odict behave different than dict?

I still believe that the concept of an ordered dictionary (behave 
like dict, only keep the order of the keys) is intuitive and doesn't 
give you so much scope for ambiguity. But probably I need to work on an 
implementation to become more clear about possible hidden subtleties.

-- Christoph
-- 
http://mail.python.org/mailman/listinfo/python-list


Re: Why are there no ordered dictionaries?

2005-11-22 Thread Kay Schluehr
Christoph Zwerschke wrote:

 That would be also biased (in favour of Python) by the fact that
 probably very little people would look for and use the package in the
 cheese shop if they were looking for ordered dicts.

Does anyone actually use this site? While the Vaults offered a nice
place and a nice interface the Cheese Shop has the appeal of a code
slum. 

Kay

-- 
http://mail.python.org/mailman/listinfo/python-list


Re: Why are there no ordered dictionaries?

2005-11-22 Thread Fuzzyman
Christoph Zwerschke wrote:
 Fredrik Lundh wrote:
[snip..]
 You're right; I found creating a Larosa/Foord OrderedDict in this
 example to be even 8 times slower than an ordinary dict. However, two
 things need to be said here: 1) The dictionary in my exmaple was pretty
 small (only 3 items), so you are not really measuring the performance of
 the ordered dict, but mainly the overhead of using a user derived class
 in comparison with the built-in dict type. And 2) the implementation by
 Larosa/Foord is very slow and can be easily improved, for instance like
 that:

 def __init__(self, init_val = ()):
  dict.__init__(self, init_val)
  self.sequence = [x[0] for x in init_val]


But that doesn't allow you to create an ordered dict from another
ordered dict.

It also allows duplicates in the sequence attribute. It's a useful idea
though.

Thanks

Fuzzyman
http://www.voidspace.org.uk/python/index.shtml

 With this change, creating the ordered dictionary is considerably faster
 and for an average size dictionary, the factor of 8 pretty quickly
 converges against 1.

 But of course, it will always be slower since it is constructed on top
 of the built-in dict. In end effect, you always have to maintain a
 sequence *plus* a dictionary, which will be always slower than a sheer
 dictionary. The ordered dictionary class just hides this uglyness of
 having to maintain a dictionary plus a sequence, so it's rather an issue
 of convenience in writing and reading programs than a performance issue.

 It may be different if the ordered dict would be implemented directly as
 an ordered hash table in C.
 
 -- Christoph

-- 
http://mail.python.org/mailman/listinfo/python-list


Re: Why are there no ordered dictionaries?

2005-11-22 Thread Fuzzyman

Kay Schluehr wrote:
 Christoph Zwerschke wrote:

  That would be also biased (in favour of Python) by the fact that
  probably very little people would look for and use the package in the
  cheese shop if they were looking for ordered dicts.

 Does anyone actually use this site? While the Vaults offered a nice
 place and a nice interface the Cheese Shop has the appeal of a code
 slum.


Hmmm.. it's *the* repository for Python code. I expect quite a few
people use it...

:-)

Fuzzyman
http://www.voidspace.org.uk/python/index.shtml

 Kay

-- 
http://mail.python.org/mailman/listinfo/python-list


Re: Why are there no ordered dictionaries?

2005-11-22 Thread Steven D'Aprano
On Tue, 22 Nov 2005 09:20:34 +0100, Fredrik Lundh wrote:

 Tom Anderson wrote:
 
 Incidentally, can we call that the Larosa-Foord ordered mapping?
 
 The implementation, sure.
 
 Then it sounds like some kind of rocket science discrete mathematics stuff
 
 But math folks usually name things after the person(s) who came
 up with the idea, not just some random implementer.

No no no! In maths things are usually named after Euler, or the first
person to discover them after Euler.


-- 
Steven.

-- 
http://mail.python.org/mailman/listinfo/python-list


Re: Why are there no ordered dictionaries?

2005-11-22 Thread Magnus Lycka
Christoph Zwerschke wrote:
 But please see my other reply: If the dictionary has more than 3 items 
 (say 10 or 20), and an effective ordered dict is used, it's not really 
 a lot slower. At least if we are talking about a situation were on 
 demand is always. So, on the other side there isn't such a big 
 performance loss when using ordered dictionaries as well.

There is no performance issue involved with this usecase at all!

It doesn't matter if it's hundreds of tuples of strings in a list
if it's supposed to be presented in a GUI. Recreating a dict from
that is bound to be magnitudes faster than getting the stuff
visible on the screen, at least if we're talking web apps. So is
using a reasonable odict implementation, if that's what you want.

I think the issue is not to overload the already extensive standard
library with trivial things that can easily be replaced by your own
three line wrapper, especially if there are a number of different
semantics that could be imagined for such a thingie.

The C++ std lib has an ordered dict class called map, and that's
ordered by key. Others suggested ordering by value, and there are a
number of different interpretations of the 'order by insertion time'
theme in the air. This clearly smells like fix your own thing and
leave it out of the standard library.

With one of these solutions picked as Python's ordered dict, we'll
make things slightly more convenient for a few programmers and just
burden others with something that sounds right for them, but turns
out not to solve their problems. Or, we could try to make a bunch
of different solution, increasing the cognitive burden for all who
learn Python while solving non-problems. This just isn't going to
happen!
-- 
http://mail.python.org/mailman/listinfo/python-list


Re: Why are there no ordered dictionaries?

2005-11-22 Thread [EMAIL PROTECTED]

Bengt Richter wrote:
 Ok, so if not in the standard library, what is the problem? Can't find what
 you want with google and PyPI etc.? Or haven't really settled on what your
 _requirements_ are? That seems to be the primary problem people who complain
 with why no sprollificator mode? questions. They don't know what they really
 mean when it comes down to a DYFR (Define Your Felicitous Requirements) 
 challenge.
 So DYFR ;-)
Beat me. I am not the one asking the question.

   parsing or not parsing is not the point, and parsing/converting is
   still create a new view of an existing data structure.
 
 So you'd like the mechanics to be automated and hidden? Then you need to
 DYFR for using the black box you want. Methods, semantics.
Lose you. don't know what you want to say.

-- 
http://mail.python.org/mailman/listinfo/python-list


Re: Why are there no ordered dictionaries?

2005-11-22 Thread [EMAIL PROTECTED]

Christoph Zwerschke wrote:
 Bengt Richter schrieb:
  Ok, so if not in the standard library, what is the problem? Can't find what
  you want with google and PyPI etc.? Or haven't really settled on what your
  _requirements_ are? That seems to be the primary problem people who complain
  with why no sprollificator mode? questions.

 What I don't understand is why legitimate questions such as why are
 there no ordered dictionaries are immediately interpreted as
 *complaints* and not just as questions. If I ask such a question, I am
 not complaining but trying to simply figure out *why* there is no such
 thing. Probably there are reasons and all I want to know is find these
 reasons and learn a little bit more about Python in doing so.

 Why can't such questions be discussed in a factual, calm and friendly way?


Using why can't is already too much. Even you turn it into is there
a thing for ordered dict, you would get similar treatment

Get used to it :-)

   They don't know what they really mean when it comes down to a DYFR
   (Define Your Felicitous Requirements) challenge.

 I don't think that this was true in this case, and even if this is the
 outcome, those who asked the question will have learned something.

 I think a discussion group is not there for only presenting mature,
 sophisticated thoughts and concepts, but also for thinking loud
 together with other about these issues. We all know that clarifying our
 thoughts works often best if you discuss them with others. And I think
 that's one purpose of discussion lists. Asking questions should not be
 immediately be discouraged, even silly questions. If it is really a FAQ,
 you can simply point to the FAQ or add the answer in the FAQ list if it
 is missing there.
Well, different groups has different personality, just don't be
scared.

-- 
http://mail.python.org/mailman/listinfo/python-list


Re: Why are there no ordered dictionaries?

2005-11-22 Thread [EMAIL PROTECTED]

Christoph Zwerschke wrote:
 Fredrik Lundh wrote:
  I'll repeat this one last time: for the use cases presented by Zwerschke
  and bonono, using a list as the master data structure, and creating the
  dictionary on demand, is a lot faster than using a ready-made ordered
  dict implementation.  if you will access things via the dictionary a lot,
  you can cache the dictionary somewhere.  if not, you can recreate it
  several times and still get a net win.

 You're right in pointing out that the advantage of ordered dictionaries
 (unless you use an omptimized C implementation) is not a performance gain.

 But please see my other reply: If the dictionary has more than 3 items
 (say 10 or 20), and an effective ordered dict is used, it's not really
 a lot slower. At least if we are talking about a situation were on
 demand is always. So, on the other side there isn't such a big
 performance loss when using ordered dictionaries as well.

 The advantage of using an ordered dictionary is that you can set up your
 ordered dictionary (say, describing your database columns) once, and
 then can access it in any way you like in the following: Iterate over it
 in a guaranteed order or access item, always refering to the same
 object, without needing to care about building and caching auxiliary
 objects with different names depending on what you are doing.

Well, I don't think performance is the concern(at least not for me),
but how best to blend with the rest of the code which I have no
interest to explain as I am not here to convincing anyone for such a
thing. I just present a use case, if they see it, fine. If not, that is
fine too.

But I did learn something that creating a dict on a list cost me
nothing, I would be less worry about the performance hit in the future.

-- 
http://mail.python.org/mailman/listinfo/python-list


Re: Why are there no ordered dictionaries?

2005-11-22 Thread A.M. Kuchling
On 22 Nov 2005 01:41:44 -0800, 
Kay Schluehr [EMAIL PROTECTED] wrote:
 Does anyone actually use this site? While the Vaults offered a nice
 place and a nice interface the Cheese Shop has the appeal of a code
 slum. 

Looking at the Cheese Shop's home page at
http://cheeseshop.python.org/pypi, which lists recent package updates,
three packages were updated on 11/22, and three on 11/21.  Two on
11/20, six on 11/19 (someone was busy!).

Looking at the Vaults's 'latest' page at
http://py.vaults.ca/apyllo.py?a=l, two packages were updated on 08/23,
and five on 08/06.  

What would improve the Cheese Shop's interface for you?

--amk
-- 
http://mail.python.org/mailman/listinfo/python-list


Re: Why are there no ordered dictionaries?

2005-11-22 Thread Kay Schluehr

A.M. Kuchling wrote:
 On 22 Nov 2005 01:41:44 -0800,
   Kay Schluehr [EMAIL PROTECTED] wrote:
  Does anyone actually use this site? While the Vaults offered a nice
  place and a nice interface the Cheese Shop has the appeal of a code
  slum.

 Looking at the Cheese Shop's home page at
 http://cheeseshop.python.org/pypi, which lists recent package updates,
 three packages were updated on 11/22, and three on 11/21.  Two on
 11/20, six on 11/19 (someone was busy!).

 Looking at the Vaults's 'latest' page at
 http://py.vaults.ca/apyllo.py?a=l, two packages were updated on 08/23,
 and five on 08/06.

 What would improve the Cheese Shop's interface for you?

 --amk

From the treasures of the vaults to cheese shops - an upside down
evolution :( Personally I find the usability of the Vaults quite well
and it's design o.k. I guess it is a technical detail that causes the
Vaults to be phased out.

If I'd try something more innovative by myself I'd think about
accessing and filtering packages through the Python console itself.
Probably an enhanced standard console enabling SQL commands. Updates of
a local database ( e.g. SQLite ) should be cheap and may be performed
by only one request. Searching, filtering, loading, installing would be
done in a Python+SQL environment. 

Kay

-- 
http://mail.python.org/mailman/listinfo/python-list


Re: Why are there no ordered dictionaries?

2005-11-22 Thread Fuzzyman
Of course ours is ordered *and* orderable ! You can explicitly alter
the sequence attribute to change the ordering.

I think we're looking at improving performance based on some of the
suggestions here - as well as possibly widening it to include some of
the alternative use cases. (Or at least Nicola Larosa will do it and
I'll criticise it).

All for another day though...

Fuzzyman
http://www.voidspace.org.uk/python/index.shtml

-- 
http://mail.python.org/mailman/listinfo/python-list


Re: Why are there no ordered dictionaries?

2005-11-22 Thread Alex Martelli
Fredrik Lundh [EMAIL PROTECTED] wrote:
   ...
 But math folks usually name things after the person(s) who came
 up with the idea, not just some random implementer.  The idea of

Wrong: you're forgetting Stigler's Law of Misonomy (which I imagine must
have NOT been discovered by Stigler...;-).  The Poisson distribution was
in fact described earlier by Bernoulli, Gosset's z-test is universally
known as Student's t-test, etc, etc.

Salsburg's delightful The Lady Tasting Tea has a lot of fun with
Stigler's law in the footnotes...;-)


Alex
-- 
http://mail.python.org/mailman/listinfo/python-list


Re: Why are there no ordered dictionaries?

2005-11-22 Thread Magnus Lycka
Christoph Zwerschke wrote:
 I still believe that the concept of an ordered dictionary (behave 
 like dict, only keep the order of the keys) is intuitive and doesn't 
 give you so much scope for ambiguity. 

Sure. Others think so too. The problem is that if you and these other
people actually write down exactly how this unambigous ordered dict
should behave, you'll end up with a dozen different sets of semantics,
which can be divided in at least three main groups.

People use different idioms, and often gather collections of classes
and functions that fit their style of coding and their typical problem
domains. There is nothing wrong with that, and they might well be made
publically available if they are more generally useful.

When adding things to the standard library, there are some more things
to consider, particularly for something general such as an odict class:
Is is general enough, and does it add enough value to outweigh the
increased cognitive burden of more classes/functions/types in the
library?

For a beginner, it's easy to believe that things would be easier if
the tool you use had already solved the problem you have at hand for
you, but it turns out that the world has so many problems, that you
would end up with a impenetrable forest of standard library modules
if we actually tried to achieve this.
-- 
http://mail.python.org/mailman/listinfo/python-list


Re: Why are there no ordered dictionaries?

2005-11-22 Thread Alex Martelli
Christoph Zwerschke [EMAIL PROTECTED] wrote:

 Alex Martelli schrieb:
  Perl hashes now keep track of 'order of keys'?  That's new to me, they
  sure didn't back when I used Perl!
 
 Maybe I shouldn't have talked about Perl when I'm an ignoramus about 
 that language... You're right, Perl has unordered arrays. That was new
 to me since I associate the term array always with ordered and I 
 just remembered that PHP's assoc arrays are similar to Perl's but in 
 fact, and the examples I have read did not mention about that problem.

Perl's _arrays_ are a bit like Python _lists_, and ordered; it's the
_hashes_ that are a bit like Python _dicts_, and unordered.  PHP's use
of array for both concepts may indeed be a bit confusing.


  What about PHP?
 
 You can conclude that PHP's assoc arrays are ordered from the fact that
 the language provides a ksort() function to order the keys. And I think
 PHP's insertion order is the one I mentioned in my last post.
 
 Anyway, it would be interesting to examine this in detail and how this
 is implemented in other languages.

Yep.  After just a bit of research I suspect you're right re PHP but
haven't found a specific reference-manual page URL about it.


  first insertion (since the last deletion if any) is ONE unambiguous
  definition, but surely not _the_ ONE with emphasis on ``the''.
  I see nothing _ambiguous_ (nor _unnatural_) in being interested in the
   *last* insertion, for example; indeed if phrased as upon insertion, put
   the key at the end of the sequence (whether it was already elsewhere in
   the sequence of not), with no need for conditionals regarding previous
  existence, it might appear more conceptually compact.
 
 But it would not satisfy the concept of keys of a dictionary which are
 always unique.

Why not?  Since keys are unique, any 'sequence' of keys is a permutation
of a set, a perfectly well-defined concept.


 BTW, there are some boundary conditions that should be fulfilled for the
 insertion order, most obviously:
 
 If you define an ordered dict that way:
 
 d = odict()
 d['a'] = 1
 d['b'] = 2
 d['c'] = 3
 
 The keys should then be orderes as ('a', 'b', 'c').

Yep, but both 'first-insertion' and 'latest-insertion' (and many other
rules) meet that constraint.


 That would be also biased (in favour of Python) by the fact that 
 probably very little people would look for and use the package in the
 cheese shop if they were looking for ordered dicts. I for example would
 probably use ordered dicts if they were part of the standard lib, but
 not if I have to install it as an obscure separate package. So I don't
 think that will give us a real clue how many people would like ordered
 dicts in the standard lib.

A package on cheese shop need not be obscure -- that depends on
announcing it well, etc.  And the standard library is so huge that many
things inside IT are in fact obscure -- I find myself often pointing out
standard-library solutions to rather experienced Pythonistas who had
been rolling their own, unaware of the stdlib alternative (thus making
the stdlib even bigger has a cost...).  So, I don't think this effect
invalidates the experiment; while not all who download an add-on would
like it in the stdlib, and vice versa, there is surely a correlation
between amount of interest/need for the add-on's functionality, and both
rate of downloads as well as interest in having it in the stdlib.

 But anyway, if I find some time, I will research a little bit more about
 the issue and create such a package, because it seems to me that the 
 existing packages and recipes are not really satisfying and you're right
 it seems to be reasonably easy. It's on my todo list now...

It presumably should have a C implementation for speed and a Python one
for wide availability and ease of installation (the latter gives all the
advantages of prototyping in fixing the API c, and is made especially
easy by the existence of UserDict.DictMixin in the stdlib).  I'll be
glad to help out with the C part when it gets to that, just holler...


Alex
-- 
http://mail.python.org/mailman/listinfo/python-list


Re: Why are there no ordered dictionaries?

2005-11-22 Thread Stuart McGraw

A.M. Kuchling [EMAIL PROTECTED] wrote in message news:[EMAIL PROTECTED]
[...]
 What would improve the Cheese Shop's interface for you?

Getting rid of those damn top level links to old versions.  
Seeing a long list of old versions, when 99% of visitors are
only interested in the current version, is just visual noise, 
and really lame.  Move the old version links onto the page
describing the software.


-- 
http://mail.python.org/mailman/listinfo/python-list


Re: Why are there no ordered dictionaries?

2005-11-22 Thread Anton Vredegoor
Christoph Zwerschke wrote:

 But of course, it will always be slower since it is constructed on top
 of the built-in dict. In end effect, you always have to maintain a
 sequence *plus* a dictionary, which will be always slower than a sheer
 dictionary. The ordered dictionary class just hides this uglyness of
 having to maintain a dictionary plus a sequence, so it's rather an issue
 of convenience in writing and reading programs than a performance issue.

 It may be different if the ordered dict would be implemented directly as
 an ordered hash table in C.

The problem with hashing is that one is storing data from a possibly
wildly varying range in a set of values with a limited range. That's
where the ordering problems come from in the first place. If one wants
to solve it once and for all one has to give up the speed advantage
that makes hashing so popular. I wonder if optimized C code using
bisect would be very much slower for small ranges?

The current set implementation uses dicts to implement sets, while sets
are a more basic data type than dicts. At least dicts and sets should
be derived from the same type. Just speaking from an intuitive point of
view of course :-)

Here's a sorted dict implementation without using hashes, which maybe
would be fast if implemented in C. The insertion order can be retrieved
using the keys and values lists from the object itself, items() gives a
sorted sequence.

Anton.

NB warning untested code.

When using mutables as keys which is possible by this implementation,
don't change the keys after they're used in the object.

from array import array

class VDict:

def __init__(self,sequence = []):
self.keys = []
self.values = []
self.unranks = array('L',[])
for key,value in sequence:
self[key] = value

def __setitem__(self,key,value):
keys = self.keys
values = self.values
unranks = self.unranks
n = len(keys)
i = self.bisect_left(key)
if i == n or keys[unranks[i]] != key:
keys.append(key)
values.append(value)
unranks.insert(i,n)
else:
values[i] = value

def __getitem__(self,key):
i = self.bisect_left(key)
return self.values[self.unranks[i]]

def bisect_left(self,key, lo=0, hi=None):
keys = self.keys
unranks = self.unranks
if hi is None:
hi = len(keys)
while lo  hi:
mid = (lo+hi)//2
if keys[unranks[mid]]  key:
lo = mid+1
else:
hi = mid
return lo

def __contains__(self,key):
keys = self.keys
unranks = self.unranks
n = len(keys)
i = self.bisect_left(key)
return i  n and keys[unranks[i]] == key

def __len__(self):
return len(self.keys)

def items(self):
keys = self.keys
values = self.values
unranks = self.unranks
return [(keys[i],values[i]) for i in unranks]

def __iter__(self):
return iter(self.items())

def remove(self,key):
keys = self.keys
values = self.values
unranks = self.unranks
n = len(keys)
i = self.bisect_left(key)
x = unranks[i]
if  i  n and keys[x] == key:
del keys[x]
del values[x]
del unranks[i]
for j,k in enumerate(unranks):
if k  x:
unranks[j] -= 1

def test():
V = VDict()
L = [1,2,3]
V[L] = 10
print V[L]
V[L] = 20
print V[L]
V.remove(L)
print V.items()
V = VDict(zip('edcba',range(5)))
print V.items()
print V['d']
V.remove('d')
print V.items()

if __name__=='__main__':
test()

-- 
http://mail.python.org/mailman/listinfo/python-list


  1   2   >