现有文件testdata.csv内容如下:

    1. name,C,Java,Python,C#,C++,id
    2. Rome,-95,96,85,63,91,826
    3. Juja,75,93,66,85,88,8984
    4. Lisi,86,76,100,93,67,10566
    5. Zhengj,-88,96,9,90,89,10588
    6. Wangx,99,96,91,88,86,10896

    读取其中数据并转为二维列表:

    1. ls = [] # 创建空列表备
    2. with open('testdata.csv','r',encoding='utf-8') as data: # 读文件,创建文件对象
    3. for line in data: # 遍历文件对象data,每次得到其一行,格式为字符串
    4. print(line) # 'Rome,-95,96,85,63,91,826\n'
    5. ls.append(line.strip().split(',')) # 文件的一行切分为元素为符串的列表加入列表中
    6. print(ls)

    输出结果为:
    [[‘name’, ‘C’, ‘Java’, ‘Python’, ‘C#’, ‘C++’, ‘id’],
    [‘Rome’, ‘-95’, ‘96’, ‘85’, ‘63’, ‘91’, ‘826’],
    [‘Juja’, ‘75’, ‘93’, ‘66’, ‘85’, ‘88’, ‘8984’],
    [‘Lisi’, ‘86’, ‘76’, ‘100’, ‘93’, ‘67’, ‘10566’],
    [‘Zhengj’, ‘-88’, ‘96’, ‘9’, ‘90’, ‘89’, ‘10588’],
    [‘Wangx’, ‘99’, ‘96’, ‘91’, ‘88’, ‘86’, ‘10896’]]

    上述功能可以用列表推导式实现,代码如下:

    1. with open('testdata.csv','r',encoding='utf-8') as data: # 读文件,创建文件对象
    2. ls = [line.strip().split(',') for line in data]

    尝试直接对其排序输出,使用sorted()函数实现:

    1. with open('testdata.csv','r',encoding='utf-8') as data: # 读文件,创建文件对象
    2. ls = [line.strip().split(',') for line in data]
    3. print(sorted(ls))

    发现结果是按 ls 元素的第一个子元素的字母表顺序进行排序输出:
    [[‘Juja’, ‘75’, ‘93’, ‘66’, ‘85’, ‘88’, ‘8984’],
    [‘Lisi’, ‘86’, ‘76’, ‘100’, ‘93’, ‘67’, ‘10566’],
    [‘Rome’, ‘-95’, ‘96’, ‘85’, ‘63’, ‘91’, ‘826’],
    [‘Wangx’, ‘99’, ‘96’, ‘91’, ‘88’, ‘86’, ‘10896’],
    [‘Zhengj’, ‘-88’, ‘96’, ‘9’, ‘90’, ‘89’, ‘10588’],
    [‘name’, ‘C’, ‘Java’, ‘Python’, ‘C#’, ‘C++’, ‘id’]]

    此时标题行参与了排序,明显不符合要求,可以将第一行先切下来,排序后再拼接到一起:

    1. with open('testdata.csv','r',encoding='utf-8') as data: # 读文件,创建文件对象
    2. ls = [line.strip().split(',') for line in data]
    3. print([ls[0]] + sorted(ls[1:])) # 将序号为 0 的元素切下来,对剩下元素进行排序,再拼接为一个新列表输出

    [[‘name’, ‘C’, ‘Java’, ‘Python’, ‘C#’, ‘C++’, ‘id’],
    [‘Juja’, ‘75’, ‘93’, ‘66’, ‘85’, ‘88’, ‘8984’],
    [‘Lisi’, ‘86’, ‘76’, ‘100’, ‘93’, ‘67’, ‘10566’],
    [‘Rome’, ‘-95’, ‘96’, ‘85’, ‘63’, ‘91’, ‘826’],
    [‘Wangx’, ‘99’, ‘96’, ‘91’, ‘88’, ‘86’, ‘10896’],
    [‘Zhengj’, ‘-88’, ‘96’, ‘9’, ‘90’, ‘89’, ‘10588’]]

    如果题目要求排序关键字不是第一个子元素时,例如要求按python成绩进行排序时,可以用lambda表达式实现。

    1. with open('testdata.csv','r',encoding='utf-8') as data: # 读文件,创建文件对象
    2. ls = [line.strip().split(',') for line in data]
    3. print([ls[0]] + sorted(ls[1:],key=lambda x:x[3])) # 根据序号为 3 的元素值排序

    [[‘name’, ‘C’, ‘Java’, ‘Python’, ‘C#’, ‘C++’, ‘id’],
    [‘Lisi’, ‘86’, ‘76’, ‘100’, ‘93’, ‘67’, ‘10566’],
    [‘Juja’, ‘75’, ‘93’, ‘66’, ‘85’, ‘88’, ‘8984’],
    [‘Rome’, ‘-95’, ‘96’, ‘85’, ‘63’, ‘91’, ‘826’],
    [‘Zhengj’, ‘-88’, ‘96’, ‘9’, ‘90’, ‘89’, ‘10588’],
    [‘Wangx’, ‘99’, ‘96’, ‘91’, ‘88’, ‘86’, ‘10896’]]

    此时注意列表中的课程成绩仍是字符串,排序时按字符串排序的结果是 ASCII 表的顺序,排序时应转为整数。从输出的可以看出,数据类型的转换并没有真实发生,只是在排序的时候按字符串对应的整数进行排序。

    1. with open('testdata.csv','r',encoding='utf-8') as data: # 读文件,创建文件对象
    2. ls = [line.strip().split(',') for line in data]
    3. print([ls[0]] + sorted(ls[1:],key=lambda x:int(x[3]))) # 字符串转整型参与排序

    [[‘name’, ‘C’, ‘Java’, ‘Python’, ‘C#’, ‘C++’, ‘id’],
    [‘Zhengj’, ‘-88’, ‘96’, ‘9’, ‘90’, ‘89’, ‘10588’],
    [‘Juja’, ‘75’, ‘93’, ‘66’, ‘85’, ‘88’, ‘8984’],
    [‘Rome’, ‘-95’, ‘96’, ‘85’, ‘63’, ‘91’, ‘826’],
    [‘Wangx’, ‘99’, ‘96’, ‘91’, ‘88’, ‘86’, ‘10896’],
    [‘Lisi’, ‘86’, ‘76’, ‘100’, ‘93’, ‘67’, ‘10566’]]
    按python成绩降序排列:

    1. with open('testdata.csv','r',encoding='utf-8') as data: # 读文件,创建文件对象
    2. ls = [line.strip().split(',') for line in data]
    3. print([ls[0]] + sorted(ls[1:],key=lambda x:int(x[3]),reverse=True)) # 字符串转整型参与排序,降序排序

    [[‘name’, ‘C’, ‘Java’, ‘Python’, ‘C#’, ‘C++’, ‘id’],
    [‘Lisi’, ‘86’, ‘76’, ‘100’, ‘93’, ‘67’, ‘10566’],
    [‘Wangx’, ‘99’, ‘96’, ‘91’, ‘88’, ‘86’, ‘10896’],
    [‘Rome’, ‘-95’, ‘96’, ‘85’, ‘63’, ‘91’, ‘826’],
    [‘Juja’, ‘75’, ‘93’, ‘66’, ‘85’, ‘88’, ‘8984’],
    [‘Zhengj’, ‘-88’, ‘96’, ‘9’, ‘90’, ‘89’, ‘10588’]]

    类似,可以要求按 C 语言成绩进行排序:

    1. with open('testdata.csv','r',encoding='utf-8') as data: # 读文件,创建文件对象
    2. ls = [line.strip().split(',') for line in data]
    3. print([ls[0]] + sorted(ls[1:],key=lambda x:int(x[1]))) # 字符串转整型参与排序

    [[‘name’, ‘C’, ‘Java’, ‘Python’, ‘C#’, ‘C++’, ‘id’],
    [‘Rome’, ‘-95’, ‘96’, ‘85’, ‘63’, ‘91’, ‘826’],
    [‘Zhengj’, ‘-88’, ‘96’, ‘9’, ‘90’, ‘89’, ‘10588’],
    [‘Juja’, ‘75’, ‘93’, ‘66’, ‘85’, ‘88’, ‘8984’],
    [‘Lisi’, ‘86’, ‘76’, ‘100’, ‘93’, ‘67’, ‘10566’],
    [‘Wangx’, ‘99’, ‘96’, ‘91’, ‘88’, ‘86’, ‘10896’]]

    按 C 语言成绩的绝对值进行排序:

    1. with open('testdata.csv','r',encoding='utf-8') as data: # 读文件,创建文件对象
    2. ls = [line.strip().split(',') for line in data]
    3. print([ls[0]] + sorted(ls[1:],key=lambda x:abs(int(x[1])))) # 字符串转整型再取绝对值后参与排序

    [[‘name’, ‘C’, ‘Java’, ‘Python’, ‘C#’, ‘C++’, ‘id’],
    [‘Juja’, ‘75’, ‘93’, ‘66’, ‘85’, ‘88’, ‘8984’],
    [‘Lisi’, ‘86’, ‘76’, ‘100’, ‘93’, ‘67’, ‘10566’],6
    [‘Zhengj’, ‘-88’, ‘96’, ‘9’, ‘90’, ‘89’, ‘10588’],
    [‘Rome’, ‘-95’, ‘96’, ‘85’, ‘63’, ‘91’, ‘826’],
    [‘Wangx’, ‘99’, ‘96’, ‘91’, ‘88’, ‘86’, ‘10896’]]
    从结果中可以看出,在排序的时候,将每个值转为其绝对值进行比较排序,输出时,还是输出该元素实际存储的数值。

    根据 id 值进行排序,id是一个序号,可以按字符串排序:

    1. with open('testdata.csv','r',encoding='utf-8') as data: # 读文件,创建文件对象
    2. ls = [line.strip().split(',') for line in data]
    3. print([ls[0]] + sorted(ls[1:],key=lambda x:x[6])) # 根据 id排序

    [[‘name’, ‘C’, ‘Java’, ‘Python’, ‘C#’, ‘C++’, ‘id’],
    [‘Lisi’, ‘86’, ‘76’, ‘100’, ‘93’, ‘67’, ‘10566’],
    [‘Zhengj’, ‘-88’, ‘96’, ‘9’, ‘90’, ‘89’, ‘10588’],
    [‘Wangx’, ‘99’, ‘96’, ‘91’, ‘88’, ‘86’, ‘10896’],
    [‘Rome’, ‘-95’, ‘96’, ‘85’, ‘63’, ‘91’, ‘826’],
    [‘Juja’, ‘75’, ‘93’, ‘66’, ‘85’, ‘88’, ‘8984’]]
    根据 id 长度进行排序:

    1. with open('testdata.csv','r',encoding='utf-8') as data: # 读文件,创建文件对象
    2. ls = [line.strip().split(',') for line in data]
    3. print([ls[0]] + sorted(ls[1:],key=lambda x:len(x[6]))) # 根据 id 长度排序

    [[‘name’, ‘C’, ‘Java’, ‘Python’, ‘C#’, ‘C++’, ‘id’],
    [‘Rome’, ‘-95’, ‘96’, ‘85’, ‘63’, ‘91’, ‘826’],
    [‘Juja’, ‘75’, ‘93’, ‘66’, ‘85’, ‘88’, ‘8984’],
    [‘Lisi’, ‘86’, ‘76’, ‘100’, ‘93’, ‘67’, ‘10566’],
    [‘Zhengj’, ‘-88’, ‘96’, ‘9’, ‘90’, ‘89’, ‘10588’],
    [‘Wangx’, ‘99’, ‘96’, ‘91’, ‘88’, ‘86’, ‘10896’]]

    可以同时按多个元素进行排序,按主次关系排序构建一个元组共同做为排序关键字,下面按C语言成绩升序排序,C语言成绩相同时,按ptyhon成绩升序排序。由元组 (int(x[2]),int(x[3])))作为排序关键字。

    1. with open('testdata.csv','r',encoding='utf-8') as data: # 读文件,创建文件对象
    2. ls = [line.strip().split(',') for line in data]
    3. print([ls[0]] + sorted(ls[1:],key=lambda x:(int(x[2]),int(x[3])))) # 将序号为2 的排序,该值相同时按序号为3的元素排序

    [[‘name’, ‘C’, ‘Java’, ‘Python’, ‘C#’, ‘C++’, ‘id’],
    [‘Lisi’, ‘86’, ‘76’, ‘100’, ‘93’, ‘67’, ‘10566’],
    [‘Juja’, ‘75’, ‘93’, ‘66’, ‘85’, ‘88’, ‘8984’],
    [‘Zhengj’, ‘-88’, ‘96’, ‘9’, ‘90’, ‘89’, ‘10588’],
    [‘Rome’, ‘-95’, ‘96’, ‘85’, ‘63’, ‘91’, ‘826’],
    [‘Wangx’, ‘99’, ‘96’, ‘91’, ‘88’, ‘86’, ‘10896’]]

    下面按C语言成绩升序排序,C语言成绩相同时,按ptyhon成绩降序排序。因成绩为数值类型,可以转换一下思路,排序时 以 -int(x[3]) 为排序依据,按 -int(x[3]) 升序排序时,实际上是按 int(x[3]) 降序排序。所以可以由元组 (int(x[2]),-int(x[3])))作为排序关键字,使两个关键字可以按相同的规则同时升序或降序排序。

    1. with open('testdata.csv','r',encoding='utf-8') as data: # 读文件,创建文件对象
    2. ls = [line.strip().split(',') for line in data]
    3. print([ls[0]] + sorted(ls[1:],key=lambda x:(int(x[2]),-int(x[3])))) # 将序号为 2 升序,该值相同时按序号为3的元素降序

    [[‘name’, ‘C’, ‘Java’, ‘Python’, ‘C#’, ‘C++’, ‘id’],
    [‘Lisi’, ‘86’, ‘76’, ‘100’, ‘93’, ‘67’, ‘10566’],
    [‘Juja’, ‘75’, ‘93’, ‘66’, ‘85’, ‘88’, ‘8984’],
    [‘Wangx’, ‘99’, ‘96’, ‘91’, ‘88’, ‘86’, ‘10896’],
    [‘Rome’, ‘-95’, ‘96’, ‘85’, ‘63’, ‘91’, ‘826’],
    [‘Zhengj’, ‘-88’, ‘96’, ‘9’, ‘90’, ‘89’, ‘10588’]]