2

I need to sort a list of strings.

However, I do not want to sort it using the first character, so I cannot use .sort()

I have a list:

records = ["Bibble - 1300 / 2000",
"Jim Foo - 900 / 2000",
"Bibble - 1600 / 2000",
"Bibble - 1000 / 2000"]

I want to sort by their score out of 2000. I want an output that looks something like this:

>>> Jim Foo - 900 / 2000
Bibble - 1000 / 2000
Bibble - 1300 / 2000
Bibble - 1600 / 2000

In the example above, I sorted it by smallest to largest. I also want to know how I would sort this list biggest score to smallest score.

I've tried .sort(), but It's nothing like what I want. .sort() sorts it with the first character which I do not want:

>>> records.sort()
>>> records
['Bibble - 1000 / 2000', 'Bibble - 1300 / 2000', 'Bibble - 1600 / 2000', 'Jim Foo - 900 / 2000']
>>> 

Is there anyway of doing this, possibly in regular expression?

Is it also possible, so if i were to add more scores into the list I would still be able to sort it this way?

2
  • you need to specify key when you call sort. Commented Mar 11, 2015 at 21:03
  • @HuStmpHrrr What do you mean? Sorry, I do not know what a key is. I mean, I do in dictionaries but not in this example. Commented Mar 11, 2015 at 21:04

5 Answers 5

3

You can use sorted function with a proper key and use re.split :

>>> import re
>>> sorted(records,key=lambda x:int(re.split(r'[-/]',x)[1].strip()))
['John Smith - 900 / 2000',
 'Bob Foo - 1000 / 2000', 
 'Bob Foo - 1300 / 2000', 
 'Bob Foo - 1600 / 2000']

The sorted function sort your list based on its key function, and your key split your elements with re.split with function as following :

re.split(r'[-/]',x)

the pattern [-/] split your string based on - or /.

for example :

>>> re.split(r'[-/]',"Bob Foo - 1600 / 2000")
['Bob Foo ', ' 1600 ', ' 2000']

and then you need to strip() to remove the leading and trailing spaces. then convert to int and sort your list based on that value!

Sign up to request clarification or add additional context in comments.

4 Comments

This works and is great because it's on one line. However, could you explain what it does at what point?
(r'[-/]',x) I'm a little confused with this line, could you go over it in your answer?
@BlaZe added in answer!
Works perfectly and now I understand how it all works. Will accept this as the answer asap!
0
def f(e):
    a, b = map(float, e.split('-')[1].split('/'))
    return a / b

records.sort(key=f)

2 Comments

As long as b is always 2000, as specified, it can be ignored. But this would work even if that changes. A could then be returned as an int rather than a float.
@TerryJanReedy yes, more generic than required.
0

Use the key attribute of the sort method:

import re
records.sort(key = lambda x: int(re.split('[-/]', x)[1]))

re.split splits x into parts whenewer it encounters a - or / character - that's what the [-/] expression stands for. Then we select the second part, convert it to an integer and use this value for sorting.

Comments

0
>>> import re
>>> records = ["Bob Foo - 1300 / 2000",
"John Smith - 900 / 2000",
"Bob Foo - 1600 / 2000",
"Bob Foo - 1000 / 2000"]
>>> def get_score(s):
    m = re.match(r'.* - (\d+) / 2000', s)
    return 0 if m is None else int(m.group(1))

>>> sorted(records, key=get_score)
['John Smith - 900 / 2000', 'Bob Foo - 1000 / 2000', 'Bob Foo - 1300 / 2000', 'Bob Foo - 1600 / 2000']

get_score will calculate the key of each record, and sort or sorted will sort records according to this value.

Comments

-2
  1. sort accepts optional key parameter. E.g. if you want to sort int list by power of number you can do something like [-3, 2, 1].sort(key=lambda x: x *x)

  2. I'm pretty sure you can write function which extracts number 1000 from "Boo Foo - 1000 / 2000". Hint: use split.

Comments

Your Answer

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

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.