根据子串

时间:2018-02-27 22:17:15

标签: python sorting

我试图从数组中获取一个列表,然后拆分字符串以按最后一系列6个数字顺序对列表进行排序(例如' 042126)。要做到这一点,我会用'。',使用字符串[-2]的第二个到最后一个分割,然后用这个子字符串对匹配文件[1]进行排序。

文件应最终排序如下: erl1.041905,erl1.041907,erl2.041908,erl1.041909,erl2.041910等。

两个问题:如何为每个字符串指定无限数量的分割(如果名称较长,使用额外的'。'?我使用4个分割,但这种情况可能无法保留。否则,如何我会两次分开工作吗?

更重要的是,我收到了一条错误:' list'对象不可调用。我做错了什么?

谢谢

matchfiles = [ [1723], ['blue.2017-09-05t15-15-07.erl1.041905.png', 
                        'blue.2017-09-05t15-15-11.erl1.041907.png', 
                        'blue.2017-09-05t15-15-14.erl1.041909.png', 
                        'blue.2017-09-05t14-21-35.erl2.041908.png', 
                        'blue.2017-09-05t14-21-38.erl2.041910.png', 
                        'blue.2017-09-05t14-21-41.erl2.041912.png', 
                        'blue.2017-09-05t14-21-45.erl2.041914.png'], 
                        [09302] ]

matchtry = sorted(matchfiles[1], key = [i.split('.', 4)[-2] for i in 
matchfiles[1]])

4 个答案:

答案 0 :(得分:1)

  • key参数需要一个函数,但是你给它一个列表,因此错误list is not callable

  • 你应该使用split('.')[-2],它总是采用倒数第二个元素。


matchfiles = [ [1723], ['blue.2017-09-05t15-15-07.erl1.041905.png',
                        'blue.2017-09-05t15-15-11.erl1.041907.png',
                        'blue.2017-09-05t15-15-14.erl1.041909.png',
                        'blue.2017-09-05t14-21-35.erl2.041908.png',
                        'blue.2017-09-05t14-21-38.erl2.041910.png',
                        'blue.2017-09-05t14-21-41.erl2.041912.png',
                        'blue.2017-09-05t14-21-45.erl2.041914.png'],
                        [9302] ]

matchtry = sorted(matchfiles[1], key=lambda x: x.rsplit('.')[-2])
print(matchtry)
# ['blue.2017-09-05t15-15-07.erl1.041905.png', 'blue.2017-09-05t15-15-11.erl1.041907.png', 
   'blue.2017-09-05t14-21-35.erl2.041908.png', 'blue.2017-09-05t15-15-14.erl1.041909.png',
   'blue.2017-09-05t14-21-38.erl2.041910.png', 'blue.2017-09-05t14-21-41.erl2.041912.png',
   'blue.2017-09-05t14-21-45.erl2.041914.png']

答案 1 :(得分:1)

key sorted参数需要一个函数。 [i.split('.', 4)[-2] for i in matchfiles[1]]是一个列表,而不是一个函数。期望的函数作用于列表中的单个元素,因此您需要一个带有字符串的函数,将其拆分为“。”字符,并返回第二个最后一列,可能转换为整数。

此外,Python不允许整数以零开头,因此您必须将[09302]更改为[9302]。 (以0开头表示该数字将是非小数。在Python 2中,0427将是427八进制,但在Python 3中,八进制数必须以0o开头。 09302在两个版本中均无效,因为八进制数不能包含9。)

matchfiles = [ [1723], ['blue.2017-09-05t15-15-07.erl1.041905.png',
                        'blue.2017-09-05t15-15-11.erl1.041907.png',
                        'blue.2017-09-05t15-15-14.erl1.041909.png',
                        'blue.2017-09-05t14-21-35.erl2.041908.png',
                        'blue.2017-09-05t14-21-38.erl2.041910.png',
                        'blue.2017-09-05t14-21-41.erl2.041912.png',
                        'blue.2017-09-05t14-21-45.erl2.041914.png'],
                        [9302] ]

matchtry = sorted(matchfiles[1], key = lambda str: int(str.split('.')[-2]))

答案 2 :(得分:1)

请记住,sorted的键参数接受iterable的每个元素(在您的情况下为list)并将其转换为某个值。按键转换后的每个元素的值确定排序顺序。因此,每次使其工作的一种简单方法是定义一个函数 采用一个元素并将其转换为易于排序的元素:

def fname_to_value(fname):
    name, ext = os.path.splitext(fname) # remove extension 
    number = name.split('.')[-1]  # Get the last set of stuff after the last '.'
    return number  # no need to convert to int, string compare does what you want

所以现在你有一个将文件名转换为可排序值的函数。简单地提供这个作为关键参数排序并且你已经完成了。

matchtry = sorted(matchfiles[1], key = fname_to_value)
for match in matchtry:
    print(match)

结果:

blue.2017-09-05t15-15-07.erl1.041905.png
blue.2017-09-05t15-15-11.erl1.041907.png
blue.2017-09-05t14-21-35.erl2.041908.png
blue.2017-09-05t15-15-14.erl1.041909.png
blue.2017-09-05t14-21-38.erl2.041910.png
blue.2017-09-05t14-21-41.erl2.041912.png
blue.2017-09-05t14-21-45.erl2.041914.png

然后,您可以根据需要处理结果列表。

答案 3 :(得分:1)

是的,问题是你的关键。您可以使用lambda表达式:https://en.wikipedia.org/wiki/Anonymous_function#Python

想象一下这是一张数学地图。用于排序的键需要一个函数,因此您可以定义一个lambda,如:

lambda curr: curr.split('.')[-2]

这为列表中的每个当前对象命名为“curr”,并应用以下表达式: 所以在你的情况下,这应该做的事情:

matchtry = sorted(matchfiles[1], key=lambda curr: curr.split('.')[-2])