Python 使用';itemgetter';根据字典元组中的最后一个、第一个名称排序?
我的程序将我的输入读入词典,将其格式化为标题格式,然后输出以供阅读。我们不使用类似于Python 使用';itemgetter';根据字典元组中的最后一个、第一个名称排序?,python,sorting,python-3.x,dictionary,Python,Sorting,Python 3.x,Dictionary,我的程序将我的输入读入词典,将其格式化为标题格式,然后输出以供阅读。我们不使用类似于dictreader的东西。我想使用itemgetter按姓氏排序,然后按名字排序。正如您所看到的,我有一个使用lambda函数的工作版本的代码,因此我希望使用前面提到的itemgetter函数得到相同的结果 import sys from operator import itemgetter, attrgetter, methodcaller def data_2_dict(line): # con
dictreader
的东西。我想使用itemgetter
按姓氏排序,然后按名字排序。正如您所看到的,我有一个使用lambda
函数的工作版本的代码,因此我希望使用前面提到的itemgetter
函数得到相同的结果
import sys
from operator import itemgetter, attrgetter, methodcaller
def data_2_dict(line):
# constants
NAME = 0
ADDR = 1
ADDR2 = 2
CITY = 3
STATE = 4
ZIP = 5
# split line and populate dictionary
line = line.rstrip('\n')
element = line.split(',')
data_dict = {
'Name' : tuple(element[NAME].split(' ')),
'Address' : element[ADDR],
'Address2' : element[ADDR2],
'City' : element[CITY],
'State' : element[STATE],
'Zip' : element[ZIP],
}
return format_data(data_dict)
def format_data(dict):
for key, value in dict.iteritems():
if key != 'Name' and key != 'State' and key != 'Zip':
dict[key] = value.title()
elif key == 'Name':
dict[key] = (value[0].title(), value[1].title())
return dict
def main():
# gather in and out file, open objects
infile = sys.argv[1]
outfile = sys.argv[2]
cust_list = []
with open(infile, 'r') as myinfile:
for line in myinfile.read().splitlines():
data = data_2_dict(line)
cust_list.append(data)
# cust_list_sorted = sorted(cust_list, key=lambda key: (key['Name'][1], key['Name'][0]))
cust_list_sorted = sorted(cust_list, key=itemgetter('Name'[1], 'Name'[0]))
with open(outfile, 'w') as myoutfile:
for line in cust_list_sorted:
nameLine = 'Name: {0}, {1} ---\n'.format(line['Name'][1], line['Name'][0])
myoutfile.write(nameLine)
addrLine = '\tAddress: {0}, {1} {2}\n'.format(line['Address'],line['City'], line['State'])
myoutfile.write(addrLine)
一行输入如下所示:
MICHELLE FULLER,265 MADEIRA AVE,,CHILLICOTHE,OH,00045
Name: Fuller, Michelle ---
Address: 265 Madeira Ave, Chillicothe OH
cust_list_sorted = sorted(
cust_list, key=lambda c, name=itemgetter('Name'): (name(c)[1], name(c)[0]))
一行输出应该如下所示:
MICHELLE FULLER,265 MADEIRA AVE,,CHILLICOTHE,OH,00045
Name: Fuller, Michelle ---
Address: 265 Madeira Ave, Chillicothe OH
cust_list_sorted = sorted(
cust_list, key=lambda c, name=itemgetter('Name'): (name(c)[1], name(c)[0]))
这在
itemgetter
中是不可能的,它返回一个从其操作数获取项的可调用项,因为您希望它做的是从其操作数的项“Name”中获取项0
如果必须使用
itemgetter
,只需将“FirstName”和“LastName”拆分并存储在字典中,然后使用itemgetter(“LastName”、“FirstName”)
这在itemgetter
中是不可能的,它返回一个可调用项,从其操作数中获取项,因为您希望它做的是从其操作数的项“Name”中提取项0
如果必须使用
itemgetter
,您可以将“FirstName”和“LastName”拆分并存储在字典中,然后使用itemgetter(“LastName”、“FirstName”)
您可以这样做:
MICHELLE FULLER,265 MADEIRA AVE,,CHILLICOTHE,OH,00045
Name: Fuller, Michelle ---
Address: 265 Madeira Ave, Chillicothe OH
cust_list_sorted = sorted(
cust_list, key=lambda c, name=itemgetter('Name'): (name(c)[1], name(c)[0]))
这将为
'Name'
创建一个itemgetter
,然后在lambda
中使用它,该lambda以(lastname,firstname)
的相反顺序返回元组
MICHELLE FULLER,265 MADEIRA AVE,,CHILLICOTHE,OH,00045
Name: Fuller, Michelle ---
Address: 265 Madeira Ave, Chillicothe OH
cust_list_sorted = sorted(
cust_list, key=lambda c, name=itemgetter('Name'): (name(c)[1], name(c)[0]))
这将为'Name'
创建一个itemgetter
,然后在lambda
中使用它,该lambda以(lastname,firstname)
的相反顺序返回元组(这主要是对的扩展,前面有一段关于Python中缺少函数组合的温和咆哮)
如果Python有一个内置的函数组合操作符(比如,∘代码>),您可以编写:
cust_list_sorted = sorted(cust_list, key=itemgetter(1, 0)∘itemgetter('Name'))
唉,Python没有(而且在可预见的将来也不会)这样的操作符,这意味着您可以编写
但这显然比
cust_list_sorted = sorted(cust_list, key=lambda obj: obj['Name'][::-1])
(比您已有的版本略短)
问题是itemgetter
无法深入到嵌套数据结构中。如果像这样展平对象:
data_dict = {
'FirstName' : element[NAME].split(' ')[0],
'LastName' : element[NAME].split(' ')[1],
'Address' : element[ADDR],
'Address2' : element[ADDR2],
'City' : element[CITY],
'State' : element[STATE],
'Zip' : element[ZIP],
}
然后您可以将itemgetter
与
cust_list_sorted = sorted(cust_list, key=itemgetter('LastName', 'FirstName'))
(这主要是对Python的扩展,开头是对Python中缺少函数组合的温和抨击。)
如果Python有一个内置的函数组合操作符(比如,∘代码>),您可以编写:
cust_list_sorted = sorted(cust_list, key=itemgetter(1, 0)∘itemgetter('Name'))
唉,Python没有(而且在可预见的将来也不会)这样的操作符,这意味着您可以编写
但这显然比
cust_list_sorted = sorted(cust_list, key=lambda obj: obj['Name'][::-1])
(比您已有的版本略短)
问题是itemgetter
无法深入到嵌套数据结构中。如果像这样展平对象:
data_dict = {
'FirstName' : element[NAME].split(' ')[0],
'LastName' : element[NAME].split(' ')[1],
'Address' : element[ADDR],
'Address2' : element[ADDR2],
'City' : element[CITY],
'State' : element[STATE],
'Zip' : element[ZIP],
}
然后您可以将itemgetter
与
cust_list_sorted = sorted(cust_list, key=itemgetter('LastName', 'FirstName'))
不过,我们自己实现组合并不难,有些库提供了这样的元函数。组合运算符的美妙之处在于,它比组合(itemgetter(1,0),itemgetter('Name'))之类的东西要简单得多,并且可以在足够低的级别上实现,比用户定义的可调用函数更高效。(itemgetter('Name')
本身很容易用lambda obj:obj['Name']
实现,但它是作为lambda
表达式的有效替代品引入的。)不过,我们自己实现组合并不难,有些库提供了这样的元函数。组合运算符的美妙之处在于,它比组合(itemgetter(1,0),itemgetter('Name'))之类的东西要简单得多,并且可以在足够低的级别上实现,比用户定义的可调用函数更高效。(itemgetter('Name')
本身很容易用lambda obj:obj['Name']
实现,但它是作为lambda
表达式的有效替代品引入的。)