Re: Sort list of dictionaries

2015-03-03 Thread Steven D'Aprano
Charles Heizer wrote:

 Hello,
 I'm new to python and I'm trying to find the right way to solve this issue
 I have.
 
 I'm trying to sort this list by name and then by version numbers. The
 problem I'm having is that I can not get the version numbers sorted with
 the highest at the top or sorted properly.
 
 mylist = [{'name': u'com.google.earth', 'version': u'7.1.2.2041'},
 {'name': u'com.google.earth', 'version': u'7.1.2.2019'},
 {'name': u'com.google.Chrome', 'version': u'40.0.2214.93'},
 {'name': u'com.google.Chrome', 'version': u'40.0.2214.91'},
[...]
 ]
 
 sortedlist = sorted(mylist , key=lambda x, y: x['name']
 LooseVersion(elem['version'])), reverse=True)

There's a syntax error there. Is there supposed to be a comma between the 
x['name'] and the LooseVersion function call?

Once you've fixed the syntax error, you can then fix the mysterious elem, 
and the fact that your key function takes too many arguments.

The key function should take *one* argument, which in your case is a dict. 
So:

def sort_by_version(d):
name = d['name']
version = d['version']
return (name, [int(substr) for substr in version.split('.')])


sortedlist = sorted(mylist, key=sort_by_version)


should get you started. It may not quiet do what you want, but you can 
adjust the sort_by_version function as needed.



-- 
Steve

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


Re: Sort list of dictionaries

2015-03-03 Thread Chris Angelico
On Wed, Mar 4, 2015 at 2:56 AM, Charles Heizer ceh...@gmail.com wrote:
 Personally, I prefer to not use a lambda:

 def name_version(elem):
 return elem['name'], LooseVersion(elem['version'])

 result = sorted(mylist, key=name_version, reverse=True)

 Peter, thank you. Me being new to Python why don't you prefer to use a lambda?

Using lambda is fine if it's really clear what's going on (usually, if
it's an extremely simple function), but if your expression goes across
multiple lines because of the function parameter, it's usually simpler
to break the function out into a separate def statement and then use
that. There's ultimately no difference[1] between a lambda function
and a def function, apart from the fact that a function created with
lambda always has the name lambda.

ChrisA

[1] Modulo bugs, eg a weird edge case with lambda and yield; certainly
no intentional difference.
-- 
https://mail.python.org/mailman/listinfo/python-list


Re: Sort list of dictionaries

2015-03-03 Thread Charles Heizer
On Monday, March 2, 2015 at 11:23:37 AM UTC-8, Peter Otten wrote:
 Charles Heizer wrote:
 
  Never mind, the light bulb finally went off. :-\
  
  sortedlist = sorted(mylist , key=lambda elem: %s %s % ( elem['name'],
  (..join([i.zfill(5) for i in elem['version'].split(.)])) ),
  reverse=True)
 
 This lightbulb will break with version numbers  9 ;)
 
 Here are two alternatives:
 
 result = sorted(
 mylist,
 key=lambda elem: (elem['name'], LooseVersion(elem['version'])),
 reverse=True)
 
 result = sorted(
 mylist,
 key=lambda e: (e[name], tuple(map(int, e[version].split(.,
 reverse=True)
 
 
 Personally, I prefer to not use a lambda:
 
 def name_version(elem):
 return elem['name'], LooseVersion(elem['version'])
 
 result = sorted(mylist, key=name_version, reverse=True)

Peter, thank you. Me being new to Python why don't you prefer to use a lambda?
-- 
https://mail.python.org/mailman/listinfo/python-list


Re: Sort list of dictionaries

2015-03-03 Thread Paul Moore
On Tuesday, 3 March 2015 16:09:31 UTC, Chris Angelico  wrote:
 On Wed, Mar 4, 2015 at 2:56 AM, Charles Heizer wrote:
  Personally, I prefer to not use a lambda:
 
  def name_version(elem):
  return elem['name'], LooseVersion(elem['version'])
 
  result = sorted(mylist, key=name_version, reverse=True)
 
  Peter, thank you. Me being new to Python why don't you prefer to use a 
  lambda?
 
 Using lambda is fine if it's really clear what's going on (usually, if
 it's an extremely simple function), but if your expression goes across
 multiple lines because of the function parameter, it's usually simpler
 to break the function out into a separate def statement and then use
 that. There's ultimately no difference[1] between a lambda function
 and a def function, apart from the fact that a function created with
 lambda always has the name lambda.
 
 ChrisA
 
 [1] Modulo bugs, eg a weird edge case with lambda and yield; certainly
 no intentional difference.

The main point is that a def gives your function a name, whereas lambda is 
unnamed. It sometimes feels harder to have to think of a name for something 
that seems simple, like your key function. But when you come back to it in a 
few months, the name is incredibly useful documentation as to what's going on.

Paul
-- 
https://mail.python.org/mailman/listinfo/python-list


Re: Sort list of dictionaries

2015-03-03 Thread Peter Otten
Charles Heizer wrote:

 On Monday, March 2, 2015 at 11:23:37 AM UTC-8, Peter Otten wrote:
 Charles Heizer wrote:
 
  Never mind, the light bulb finally went off. :-\
  
  sortedlist = sorted(mylist , key=lambda elem: %s %s % ( elem['name'],
  (..join([i.zfill(5) for i in elem['version'].split(.)])) ),
  reverse=True)
 
 This lightbulb will break with version numbers  9 ;)
 
 Here are two alternatives:
 
 result = sorted(
 mylist,
 key=lambda elem: (elem['name'], LooseVersion(elem['version'])),
 reverse=True)
 
 result = sorted(
 mylist,
 key=lambda e: (e[name], tuple(map(int, e[version].split(.,
 reverse=True)
 
 
 Personally, I prefer to not use a lambda:
 
 def name_version(elem):
 return elem['name'], LooseVersion(elem['version'])
 
 result = sorted(mylist, key=name_version, reverse=True)
 
 Peter, thank you. Me being new to Python why don't you prefer to use a
 lambda?

I find

def name_version(elem):
return elem['name'], LooseVersion(elem['version'])

more readable than

lambda elem: (elem['name'], LooseVersion(elem['version']))

and I can understand what

 result = sorted(mylist, key=name_version, reverse=True)

is supposed to do without grokking the implementation of name_version() 
first. I can spot a potential bug -- are the names really supposed to occur 
in reverse order, not just the versions? -- again without a look at the 
implementation.

If I intend to use the script more than once or if I want to rely on the 
result I can write unit tests for name_version() to increase confidence that 
it does what I expect.

Finally I can add a docstring to make it more discoverable in the 
interactive interpreter.

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


Re: Sort list of dictionaries

2015-03-03 Thread Jason Friedman
On Tue, Mar 3, 2015 at 12:07 AM, Chris Angelico ros...@gmail.com wrote:

 Heh, I think that mght be a bit abusive :) I'm not sure that
 you want to depend on the version numbers fitting inside the rules for
 IP addresses, especially given that the example has a component of
 2214.


Indeed, I was mistaken

 ipaddress.ip_address(1000.1.2.3)
Traceback (most recent call last):
  File stdin, line 1, in module
  File /opt/python/lib/python3.4/ipaddress.py, line 54, in ip_address
address)
ValueError: '1000.1.2.3' does not appear to be an IPv4 or IPv6 address

I was overcome by how neat I think the ipaddress module is.
I have not used it yet, but I expect someday I will, and I appreciate
how Python makes my job easier by doing much of my work for me.  A
colleague yesterday asked how I guaranteed my temporary file names
would not collide with another file, and my answer was I don't have to
worry about it, someone else figured it out with the tempfile module.
-- 
https://mail.python.org/mailman/listinfo/python-list


Re: Sort list of dictionaries

2015-03-03 Thread Chris Angelico
On Wed, Mar 4, 2015 at 1:45 AM, Jason Friedman jsf80...@gmail.com wrote:
 I appreciate
 how Python makes my job easier by doing much of my work for me.  A
 colleague yesterday asked how I guaranteed my temporary file names
 would not collide with another file, and my answer was I don't have to
 worry about it, someone else figured it out with the tempfile module.

Though in that case, Python isn't actually the one doing most of the
work - the tempfile module handballs responsibility to the lower-level
functions. But yes, there's HEAPS that you don't have to worry about,
because it's Someone Else's Problem.

ChrisA
-- 
https://mail.python.org/mailman/listinfo/python-list


Re: Sort list of dictionaries

2015-03-02 Thread Jason Friedman
 This is what I was trying but LooseVersion() was not sorting version numbers 
 like I thought it would. You will notice that Chrome version 40.0.2214.111 
 is higher than 40.0.2214.91 but in the end result it's not sorting it that 
 way.

 Because it's a string they're sorted lexicographically, and in that
 ordering 40.0.2214.111 is less than 40.0.2214.91. Instead of a
 string you should probably use some sort of version info tuple. A
 simple tuple of ints may suffice, although you may need to get a
 little cleverer if there are ever any version strings that aren't
 entirely dotted numeric.

Also, Python 3.4 comes with an ipaddress module.

 import ipaddress
 address_string_1 = 2.2.3.4
 address_string_2 = 10.2.3.4
 address_string_2  address_string_1
False
 ip_address_1 = ipaddress.ip_address(address_string_1)
 ip_address_2 = ipaddress.ip_address(address_string_2)
 ip_address_2  ip_address_1
True
-- 
https://mail.python.org/mailman/listinfo/python-list


Re: Sort list of dictionaries

2015-03-02 Thread Chris Angelico
On Tue, Mar 3, 2015 at 4:33 PM, Jason Friedman jsf80...@gmail.com wrote:
 This is what I was trying but LooseVersion() was not sorting version 
 numbers like I thought it would. You will notice that Chrome version 
 40.0.2214.111 is higher than 40.0.2214.91 but in the end result it's 
 not sorting it that way.

 Because it's a string they're sorted lexicographically, and in that
 ordering 40.0.2214.111 is less than 40.0.2214.91. Instead of a
 string you should probably use some sort of version info tuple. A
 simple tuple of ints may suffice, although you may need to get a
 little cleverer if there are ever any version strings that aren't
 entirely dotted numeric.

 Also, Python 3.4 comes with an ipaddress module.

Heh, I think that mght be a bit abusive :) I'm not sure that
you want to depend on the version numbers fitting inside the rules for
IP addresses, especially given that the example has a component of
2214.

The right way to compare version numbers is usually to split them on
dots, then treat each part as a separate number. I say usually
because there are complications like alpha, RC, -git, +deb7u1,
and so on, but if the entire version number consists of digits and
dots, then tuple(int(x) for x in version_number.split(.)) will give
you a properly-sortable key.

BTW, Jason: It's usually courteous to acknowledge who you're quoting.
If you look at the top of my post here, you'll see that there's a line
saying your name and email address, and the date/time that you made
your post; but underneath that is just straight text, because your
post didn't extend the same courtesy to the previous posters. When you
trim quoted text, do please try to keep at least the first
acknowledgement line - the one showing who you're actually quoting.
Whether or not you keep additional headers is up to you (sometimes
it's easy, but other times it's fiddly), but the first one is your
responsibility. Thanks!

ChrisA
-- 
https://mail.python.org/mailman/listinfo/python-list


Re: Sort list of dictionaries

2015-03-02 Thread Charles Heizer
Sorry,

sortedlist = sorted(mylist , key=lambda elem: %s %s % (elem['name'], 
LooseVersion(elem['version'])), reverse=True)

This is what I was trying but LooseVersion() was not sorting version numbers 
like I thought it would. You will notice that Chrome version 40.0.2214.111 is 
higher than 40.0.2214.91 but in the end result it's not sorting it that way.

Thanks,
Charlie

On Monday, March 2, 2015 at 10:32:40 AM UTC-8, Emile van Sebille wrote:
 On 3/2/2015 10:17 AM, Charles Heizer wrote:
  Hello,
  I'm new to python and I'm trying to find the right way to solve this issue 
  I have.
 
  I'm trying to sort this list by name and then by version numbers. The 
  problem I'm having is that I can not get the version numbers sorted with 
  the highest at the top or sorted properly.
 
  mylist = [{'name': u'com.google.earth', 'version': u'7.1.2.2041'},
  {'name': u'com.google.earth', 'version': u'7.1.2.2019'},
  {'name': u'com.google.Chrome', 'version': u'40.0.2214.93'},
  {'name': u'com.google.Chrome', 'version': u'40.0.2214.91'},
  {'name': u'com.google.Chrome', 'version': u'40.0.2214.111'},
  {'name': u'com.google.Chrome', 'version': u'39.0.2171.99'},
  {'name': u'com.google.Chrome', 'version': u'39.0.2171.95'},
  {'name': u'com.google.Chrome', 'version': u'39.0.2171.71'},
  {'name': u'com.google.Chrome', 'version': u'38.0.2125.122'},
  {'name': u'com.google.Chrome', 'version': u'38.0.2125.111'},
  {'name': u'com.google.Chrome', 'version': u'38.0.2125.104'},
  {'name': u'com.google.Chrome', 'version': u'38.0.2125.101'},
  {'name': u'com.google.Chrome', 'version': u'37.0.2062.94'},
  {'name': u'com.google.Chrome', 'version': u'37.0.2062.120'},
  {'name': u'com.google.Chrome', 'version': u'36.0.1985.143'},
  {'name': u'com.google.Chrome', 'version': u'36.0.1985.125'},
  {'name': u'com.google.Chrome', 'version': u'35.0.1916.153'},
  {'name': u'com.google.Chrome', 'version': u'35.0.1916.114'},
  {'name': u'com.google.Chrome', 'version': u'34.0.1847.137'},
  {'name': u'com.google.Chrome', 'version': u'34.0.1847.131'},
  {'name': u'com.google.Chrome', 'version': u'34.0.1847.116'},
  {'name': u'com.google.Chrome', 'version': u'33.0.1750.152'},
  {'name': u'com.google.Chrome', 'version': u'33.0.1750.149'},
  {'name': u'com.google.Chrome', 'version': u'33.0.1750.146'},
  {'name': u'com.google.Chrome', 'version': u'32.0.1700.107'},
  {'name': u'com.google.Chrome', 'version': u'31.0.1650.63'},
  {'name': u'com.google.Chrome', 'version': u'31.0.1650.57'}]
 
  sortedlist = sorted(mylist , key=lambda x, y: x['name'] 
  LooseVersion(elem['version'])), reverse=True)
 
 You'll need to fix LooseVersion or elem or both -- or show them so we 
 can help.
 
 Emile
 
 
 
 
  Thanks,
  Charlie
 
-- 
https://mail.python.org/mailman/listinfo/python-list


Re: Sort list of dictionaries

2015-03-02 Thread Emile van Sebille

On 3/2/2015 10:17 AM, Charles Heizer wrote:

Hello,
I'm new to python and I'm trying to find the right way to solve this issue I 
have.

I'm trying to sort this list by name and then by version numbers. The problem 
I'm having is that I can not get the version numbers sorted with the highest at 
the top or sorted properly.

mylist = [{'name': u'com.google.earth', 'version': u'7.1.2.2041'},
{'name': u'com.google.earth', 'version': u'7.1.2.2019'},
{'name': u'com.google.Chrome', 'version': u'40.0.2214.93'},
{'name': u'com.google.Chrome', 'version': u'40.0.2214.91'},
{'name': u'com.google.Chrome', 'version': u'40.0.2214.111'},
{'name': u'com.google.Chrome', 'version': u'39.0.2171.99'},
{'name': u'com.google.Chrome', 'version': u'39.0.2171.95'},
{'name': u'com.google.Chrome', 'version': u'39.0.2171.71'},
{'name': u'com.google.Chrome', 'version': u'38.0.2125.122'},
{'name': u'com.google.Chrome', 'version': u'38.0.2125.111'},
{'name': u'com.google.Chrome', 'version': u'38.0.2125.104'},
{'name': u'com.google.Chrome', 'version': u'38.0.2125.101'},
{'name': u'com.google.Chrome', 'version': u'37.0.2062.94'},
{'name': u'com.google.Chrome', 'version': u'37.0.2062.120'},
{'name': u'com.google.Chrome', 'version': u'36.0.1985.143'},
{'name': u'com.google.Chrome', 'version': u'36.0.1985.125'},
{'name': u'com.google.Chrome', 'version': u'35.0.1916.153'},
{'name': u'com.google.Chrome', 'version': u'35.0.1916.114'},
{'name': u'com.google.Chrome', 'version': u'34.0.1847.137'},
{'name': u'com.google.Chrome', 'version': u'34.0.1847.131'},
{'name': u'com.google.Chrome', 'version': u'34.0.1847.116'},
{'name': u'com.google.Chrome', 'version': u'33.0.1750.152'},
{'name': u'com.google.Chrome', 'version': u'33.0.1750.149'},
{'name': u'com.google.Chrome', 'version': u'33.0.1750.146'},
{'name': u'com.google.Chrome', 'version': u'32.0.1700.107'},
{'name': u'com.google.Chrome', 'version': u'31.0.1650.63'},
{'name': u'com.google.Chrome', 'version': u'31.0.1650.57'}]

sortedlist = sorted(mylist , key=lambda x, y: x['name'] 
LooseVersion(elem['version'])), reverse=True)


You'll need to fix LooseVersion or elem or both -- or show them so we 
can help.


Emile





Thanks,
Charlie




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


Re: Sort list of dictionaries

2015-03-02 Thread Peter Otten
Charles Heizer wrote:

 Never mind, the light bulb finally went off. :-\
 
 sortedlist = sorted(mylist , key=lambda elem: %s %s % ( elem['name'],
 (..join([i.zfill(5) for i in elem['version'].split(.)])) ),
 reverse=True)

This lightbulb will break with version numbers  9 ;)

Here are two alternatives:

result = sorted(
mylist,
key=lambda elem: (elem['name'], LooseVersion(elem['version'])),
reverse=True)

result = sorted(
mylist,
key=lambda e: (e[name], tuple(map(int, e[version].split(.,
reverse=True)


Personally, I prefer to not use a lambda:

def name_version(elem):
return elem['name'], LooseVersion(elem['version'])

result = sorted(mylist, key=name_version, reverse=True)


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


Re: Sort list of dictionaries

2015-03-02 Thread Ian Kelly
On Mon, Mar 2, 2015 at 11:38 AM, Charles Heizer ceh...@gmail.com wrote:
 Sorry,

 sortedlist = sorted(mylist , key=lambda elem: %s %s % (elem['name'], 
 LooseVersion(elem['version'])), reverse=True)

 This is what I was trying but LooseVersion() was not sorting version numbers 
 like I thought it would. You will notice that Chrome version 40.0.2214.111 
 is higher than 40.0.2214.91 but in the end result it's not sorting it that 
 way.

Because it's a string they're sorted lexicographically, and in that
ordering 40.0.2214.111 is less than 40.0.2214.91. Instead of a
string you should probably use some sort of version info tuple. A
simple tuple of ints may suffice, although you may need to get a
little cleverer if there are ever any version strings that aren't
entirely dotted numeric.
-- 
https://mail.python.org/mailman/listinfo/python-list


Re: Sort list of dictionaries

2015-03-02 Thread Dave Angel

On 03/02/2015 01:38 PM, Charles Heizer wrote:

Sorry,

sortedlist = sorted(mylist , key=lambda elem: %s %s % (elem['name'], 
LooseVersion(elem['version'])), reverse=True)

This is what I was trying but LooseVersion() was not sorting version numbers like I thought it 
would. You will notice that Chrome version 40.0.2214.111 is higher than 
40.0.2214.91 but in the end result it's not sorting it that way.



Please don't top-post.  put your remarks after whatever quoting you do.

You still haven't posted your LooseVersion() function source.  I agree 
with Emile that it's likely to be the problem.



--
DaveA
--
https://mail.python.org/mailman/listinfo/python-list


Re: Sort list of dictionaries

2015-03-02 Thread Charles Heizer
Never mind, the light bulb finally went off. :-\

sortedlist = sorted(mylist , key=lambda elem: %s %s % ( elem['name'], 
(..join([i.zfill(5) for i in elem['version'].split(.)])) ), reverse=True)

On Monday, March 2, 2015 at 10:40:30 AM UTC-8, Charles Heizer wrote:
 Sorry,
 
 sortedlist = sorted(mylist , key=lambda elem: %s %s % (elem['name'], 
 LooseVersion(elem['version'])), reverse=True)
 
 This is what I was trying but LooseVersion() was not sorting version numbers 
 like I thought it would. You will notice that Chrome version 40.0.2214.111 
 is higher than 40.0.2214.91 but in the end result it's not sorting it that 
 way.
 
 Thanks,
 Charlie
 
 On Monday, March 2, 2015 at 10:32:40 AM UTC-8, Emile van Sebille wrote:
  On 3/2/2015 10:17 AM, Charles Heizer wrote:
   Hello,
   I'm new to python and I'm trying to find the right way to solve this 
   issue I have.
  
   I'm trying to sort this list by name and then by version numbers. The 
   problem I'm having is that I can not get the version numbers sorted with 
   the highest at the top or sorted properly.
  
   mylist = [{'name': u'com.google.earth', 'version': u'7.1.2.2041'},
   {'name': u'com.google.earth', 'version': u'7.1.2.2019'},
   {'name': u'com.google.Chrome', 'version': u'40.0.2214.93'},
   {'name': u'com.google.Chrome', 'version': u'40.0.2214.91'},
   {'name': u'com.google.Chrome', 'version': u'40.0.2214.111'},
   {'name': u'com.google.Chrome', 'version': u'39.0.2171.99'},
   {'name': u'com.google.Chrome', 'version': u'39.0.2171.95'},
   {'name': u'com.google.Chrome', 'version': u'39.0.2171.71'},
   {'name': u'com.google.Chrome', 'version': u'38.0.2125.122'},
   {'name': u'com.google.Chrome', 'version': u'38.0.2125.111'},
   {'name': u'com.google.Chrome', 'version': u'38.0.2125.104'},
   {'name': u'com.google.Chrome', 'version': u'38.0.2125.101'},
   {'name': u'com.google.Chrome', 'version': u'37.0.2062.94'},
   {'name': u'com.google.Chrome', 'version': u'37.0.2062.120'},
   {'name': u'com.google.Chrome', 'version': u'36.0.1985.143'},
   {'name': u'com.google.Chrome', 'version': u'36.0.1985.125'},
   {'name': u'com.google.Chrome', 'version': u'35.0.1916.153'},
   {'name': u'com.google.Chrome', 'version': u'35.0.1916.114'},
   {'name': u'com.google.Chrome', 'version': u'34.0.1847.137'},
   {'name': u'com.google.Chrome', 'version': u'34.0.1847.131'},
   {'name': u'com.google.Chrome', 'version': u'34.0.1847.116'},
   {'name': u'com.google.Chrome', 'version': u'33.0.1750.152'},
   {'name': u'com.google.Chrome', 'version': u'33.0.1750.149'},
   {'name': u'com.google.Chrome', 'version': u'33.0.1750.146'},
   {'name': u'com.google.Chrome', 'version': u'32.0.1700.107'},
   {'name': u'com.google.Chrome', 'version': u'31.0.1650.63'},
   {'name': u'com.google.Chrome', 'version': u'31.0.1650.57'}]
  
   sortedlist = sorted(mylist , key=lambda x, y: x['name'] 
   LooseVersion(elem['version'])), reverse=True)
  
  You'll need to fix LooseVersion or elem or both -- or show them so we 
  can help.
  
  Emile
  
  
  
  
   Thanks,
   Charlie
  
-- 
https://mail.python.org/mailman/listinfo/python-list


Re: Sort list of dictionaries by key (case insensitive)

2010-01-13 Thread Chris Rebert
On Tue, Jan 12, 2010 at 11:45 PM, Nico Grubert nicogrub...@gmail.com wrote:
 Hi there

 I have the following list 'mylist' that contains some dictionaries:

 mylist = [{'title':'the Fog', 'id':1},
          {'title':'The Storm', 'id':2},
          {'title':'the bible', 'id':3},
          {'title':'The thunder', 'id':4}
         ]

mylist.sort(key = lambda d: d['title'])

Use operator.itemgetter() to optimize in the unlikely event it becomes
necessary.

Cheers,
Chris
--
http://blog.rebertia.com
-- 
http://mail.python.org/mailman/listinfo/python-list


Re: Sort list of dictionaries by key (case insensitive)

2010-01-13 Thread Peter Otten
Nico Grubert wrote:

 I have the following list 'mylist' that contains some dictionaries:
 
 mylist = [{'title':'the Fog', 'id':1},
{'title':'The Storm', 'id':2},
{'title':'the bible', 'id':3},
{'title':'The thunder', 'id':4}
   ]
 
 How I can sort (case insensitive) the list by the dictioary's 'title' key?
 
 The result should be this list:
 [{'title':'the bible', 'id':3},
   {'title':'the Fog', 'id':1},
   {'title':'The Storm', 'id':2},
   {'title':'The thunder', 'id':4}
 ]
 
 I am using Python 2.4.

Python 2.4.6 (#2, Mar 19 2009, 10:02:47)
[GCC 4.3.3] on linux2
Type help, copyright, credits or license for more information.
 import locale
 locale.setlocale(locale.LC_ALL, )
'de_DE.UTF-8'
 mylist = [{'title':'the Fog', 'id':1},
...{'title':'The Storm', 'id':2},
...{'title':'the bible', 'id':3},
...{'title':'The thunder', 'id':4}
...   ]
 mylist.sort(key=lambda item: locale.strxfrm(item[title]))
 import pprint
 pprint.pprint(mylist)
[{'id': 3, 'title': 'the bible'},
 {'id': 1, 'title': 'the Fog'},
 {'id': 2, 'title': 'The Storm'},
 {'id': 4, 'title': 'The thunder'}]

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


Re: Sort list of dictionaries by key (case insensitive)

2010-01-13 Thread Chris Rebert
On Wed, Jan 13, 2010 at 2:41 AM, Chris Rebert c...@rebertia.com wrote:
 On Tue, Jan 12, 2010 at 11:45 PM, Nico Grubert nicogrub...@gmail.com wrote:
 Hi there

 I have the following list 'mylist' that contains some dictionaries:

 mylist = [{'title':'the Fog', 'id':1},
          {'title':'The Storm', 'id':2},
          {'title':'the bible', 'id':3},
          {'title':'The thunder', 'id':4}
         ]

 mylist.sort(key = lambda d: d['title'])

Er, that should have been mylist.sort(key = lambda d:
d['title'].lower())  of course.
Goes for more coffee

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


Re: Sort list of dictionaries by key (case insensitive)

2010-01-13 Thread Florian Diesch
Nico Grubert nicogrub...@gmail.com writes:

 Hi there

 I have the following list 'mylist' that contains some dictionaries:

 mylist = [{'title':'the Fog', 'id':1},
   {'title':'The Storm', 'id':2},
   {'title':'the bible', 'id':3},
   {'title':'The thunder', 'id':4}
  ]

 How I can sort (case insensitive) the list by the dictioary's 'title' key?

mylist.sort(key=lambda x: x['title'].lower())



   Florian
-- 
http://www.florian-diesch.de/software/easygconf/
-- 
http://mail.python.org/mailman/listinfo/python-list


Re: Sort list of dictionaries by key (case insensitive)

2010-01-13 Thread Nico Grubert



Er, that should have been mylist.sort(key = lambda d:
d['title'].lower())  of course.



Thanks a lot for the tip, chris.
Unfortunately, I only have Python 2.3.5 installed and can't upgrade to 
2.4 due to an underliying application server.


In python 2.3 the 'sort()' function does not excepts any keywords 
arguments (TypeError: sort() takes no keyword arguments), so is there a 
workaround?


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


Re: Sort list of dictionaries by key (case insensitive)

2010-01-13 Thread Peter Otten
Nico Grubert wrote:

 Er, that should have been mylist.sort(key = lambda d:
 d['title'].lower())  of course.
 
 
 Thanks a lot for the tip, chris.
 Unfortunately, I only have Python 2.3.5 installed and can't upgrade to
 2.4 due to an underliying application server.
 
 In python 2.3 the 'sort()' function does not excepts any keywords
 arguments (TypeError: sort() takes no keyword arguments), so is there a
 workaround?

There is a technique called decorate-sort-undecorate:

 def sorted(items, key):
... decorated = [(key(item), index, item) for index, item in 
enumerate(items)]
... decorated.sort()
... return [item[2] for item in decorated]
...
 items = Atem Äther ähnlich anders.split()
 print  .join(sorted(items, key=lambda s: s.lower()))
anders Atem Äther ähnlich
 print  .join(sorted(items, key=lambda s: locale.strxfrm(s)))
ähnlich anders Atem Äther

The above may run on 2.3, but I actually ran it on 2.6.

Peter

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


Re: Sort list of dictionaries by key (case insensitive)

2010-01-13 Thread Stefan Behnel

Peter Otten, 13.01.2010 13:25:

 items = Atem Äther ähnlich anders.split()
 print  .join(sorted(items, key=lambda s: s.lower()))


If you can make sure that 's' is either always a byte string or always a 
unicode string (which is good programming practice anyway), an unbound 
method can simplify (and speed up) the above, e.g.


sorted(items, key=unicode.lower)

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


Re: Sort list of dictionaries by key (case insensitive)

2010-01-13 Thread Nico Grubert

Thanks a lot Stefan  Peter.

I'm almost there (except sorting of umlauts does not work yet).


import locale

def sorted(items, key):
decorated = [(key(item), index, item) for index, item in
  enumerate(items)]
decorated.sort()
return [item[2] for item in decorated]

items = [{'title':'the Ähnlich', 'id':1},
 {'title':'The Storm', 'id':2},
 {'title':'the bible','id':3},
 {'title':'The thunder', 'id':4}]

print sorted(items, key=lambda d: locale.strxfrm(d.get('title')))

- [{'id': 2, 'title': 'The Storm'}, {'id': 4, 'title': 'The thunder'}, 
{'id': 3, 'title': 'the bible'}, {'id': 1, 'title': 'the \xc4hnlich'}]



The entry with the umlaut is the last item in but according to german 
umlaut rules it should be the first item in the result.

Do I have to set anything with the locale module?


Regards
Nico

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


Re: Sort list of dictionaries by key (case insensitive)

2010-01-13 Thread Stefan Behnel

Nico Grubert, 13.01.2010 16:18:

print sorted(items, key=lambda d: locale.strxfrm(d.get('title')))

- [{'id': 2, 'title': 'The Storm'}, {'id': 4, 'title': 'The thunder'}, 
{'id': 3, 'title': 'the bible'}, {'id': 1, 'title': 'the \xc4hnlich'}]


The entry with the umlaut is the last item in but according to german 
umlaut rules it should be the first item in the result.

Do I have to set anything with the locale module?


http://wiki.python.org/moin/HowTo/Sorting#Topicstobecovered

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


Re: Sort list of dictionaries by key (case insensitive)

2010-01-13 Thread Peter Otten
Nico Grubert wrote:

 Thanks a lot Stefan  Peter.
 
 I'm almost there (except sorting of umlauts does not work yet).
 
 
 import locale

locale.setlocale(locale.LC_ALL, )

 def sorted(items, key):
  decorated = [(key(item), index, item) for index, item in
enumerate(items)]
  decorated.sort()
  return [item[2] for item in decorated]
 
 items = [{'title':'the Ähnlich', 'id':1},
   {'title':'The Storm', 'id':2},
   {'title':'the bible','id':3},
   {'title':'The thunder', 'id':4}]
 
 print sorted(items, key=lambda d: locale.strxfrm(d.get('title')))
 
 - [{'id': 2, 'title': 'The Storm'}, {'id': 4, 'title': 'The thunder'},
 {'id': 3, 'title': 'the bible'}, {'id': 1, 'title': 'the \xc4hnlich'}]
 
 
 The entry with the umlaut is the last item in but according to german
 umlaut rules it should be the first item in the result.
 Do I have to set anything with the locale module?

Adding the setlocale() call will suffice provided your script uses the same 
encoding as your environment. If not something like

# -*- coding:utf-8 -*-
import locale

locale.setlocale(locale.LC_ALL, )
encoding = locale.getlocale()[1]

def sorted(items, key):
 decorated = [(key(item), index, item) for index, item in
   enumerate(items)]
 decorated.sort()
 return [item[2] for item in decorated]

# book titles use unicode
items = [{'title':u'the Ähnlich', 'id':1},
  {'title':u'The Storm', 'id':2},
  {'title':u'the bible','id':3},
  {'title':u'The thunder', 'id':4}]

def sortkey(item):
s = item[title].encode(encoding)
return locale.strxfrm(s)

print sorted(items, key=sortkey)

may be a bit more robust. If your source code doesn't use UTF-8 you have to 
modify the coding declaration at the top accordingly.

Peter

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


Re: Sort list of dictionaries by key (case insensitive)

2010-01-13 Thread Nico Grubert



http://wiki.python.org/moin/HowTo/Sorting#Topicstobecovered


Works fine. Thanks a lot for your help, Stefan.

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