2

I have a python list with filenames as follows: [name1, name10, name11, name2, name3, ..., name9].

I want it to be sorted like [name1, name2, name3, ..., name10, name11].

How can I do this?

I know that I can use a special key function (sorted(files, key=lambda name: etc.)), but I am not sure which function to apply.

Thanks for your help!

beta
  • 5,324
  • 15
  • 57
  • 99

7 Answers7

3

Try third party library for natural string sorting called natsort.

>>> import natsort
>>> my_list = [...]
>>> natsort.natsorted(my_list)

You can also specify key for sorting using key argument.

>>> natsort.natsorted(my_list, key=lambda x: ...)
Rahul Gupta
  • 46,769
  • 10
  • 112
  • 126
3

Try This :

sorted(aList, key= lambda x: (lambda a, _, b: (a, int(b)) if b.isdigit() else (float("inf"), x))(*x.partition(" ")))

This will work as per your requirement. Also it doesn't require any third party library .

coder3521
  • 2,608
  • 1
  • 28
  • 50
2

What you search for is The alphanum algorithm (sometimes also called Natural Sort). The site I linked has implementations in multiple languages, even one in python.

llogiq
  • 13,815
  • 8
  • 40
  • 72
2
import re

l = ["name1", "name10", "name 11", "name2"]
convert = lambda text: int(text) if text.isdigit() else text.lower() 
alphanum_key = lambda key: [ convert(c) for c in re.split('([0-9]+)', key) ] 
print sorted(l, key = alphanum_key)

Output: ['name1', 'name2', 'name10', 'name 11']

Avión
  • 7,963
  • 11
  • 64
  • 105
2

If you are looking for a lambda expression to use with the sorted function and know that your entries are of the form "nameXXXXX":

sorted(names, key=lambda name: int(name[4:]))
Michael Lang
  • 3,902
  • 1
  • 23
  • 37
  • 1
    Nice! Well, it's the simplest solution if you know exactly what kind of values you'll be dealing with – Michael Lang May 29 '15 at 08:40
  • But this one won't work in general , . like if a element containing Namea instead of Name .. Check the Below post for a Generic solution. – coder3521 May 29 '15 at 09:03
1

i think i got it. given a list [name1, name10, name11, name2, name3, ..., name9]

sorted(list, key = lambda name: int(name[4:]))

It strips 4 characters because name is 4 characters long and then sorts by the remaining numbers.

beta
  • 5,324
  • 15
  • 57
  • 99
1

This is an example of code that does the job. It is not optimal but it is easy to understand and gives you an insight on the logic behind the solution of this specific sorting problem.

mylist = ['name1', 'name2', 'name3', 'name10', 'name11']
sorted_list = []

for n in range(100): #this gives you the order
    for item in mylist:
        if int(item[4:]) == n:
            sorted_list.append(item)

print(sorted_list)

It will output:

['name1', 'name2', 'name3', 'name10', 'name11']
alec_djinn
  • 10,104
  • 8
  • 46
  • 71