Python lambda function to sort list according to dictionary

試著忘記壹切 提交于 2021-02-10 05:29:05

问题


The sample codes bellow retrieve all the runing procces and print them. They've bee written following the 3rd example here and final one from here. Problem is I cannot figure out why only the first one retrieves process sorted as desired.

I think it is related to the lambda function construction. But the rightly running sample, the first one, seems to mix the local p variable of the for statement with the p.dict dictionary, making me get stuck.

First Sample:

import psutil

procs = []

for p in psutil.process_iter():
    try:
        p.dict = p.as_dict(['pid', 'name'])
    except psutil.NoSuchProcess:
        pass
    else:
        procs.append(p)

processes = sorted(procs, key=lambda p: p.dict['name'], reverse=False)

print(processes)

The second sample:

import psutil

procs = []

for proc in psutil.process_iter():
    try:
        procs_dic = proc.as_dict(['pid', 'name'])
    except psutil.NoSuchProcess:
         pass
    else:
        procs.append(proc)

processes = sorted(procs, key=lambda ordem: procs_dic['name'], reverse=False)

print(processes)

回答1:


Your second code snippet's lambda looks up 'name' in the same dictionary no matter what object it's passed; how could that possibly work?

Your third doesn't even seem to be trying to sort the processes; I'm not sure what it has to do with the question.

The change you've made to turn the first snippet into the second is evidently motivated by your concern that the first

seems to mix the local p variable of the for statement with the p.dict dictionary

and I'd be happy to help but I'm afraid I don't understand what problem it is you see. Perhaps the following may help? There are two variables here called p. The first is used in the loop over processes; each time round the loop its value is a process object, and we give that process object a dict attribute containing an entry for 'name'. The second is the argument to your anonymous function (lambda): its value is also always a process object. You could give them different names if you wanted and it wouldn't break anything, but actually I think it's clearer as it is: in this little bit of code, p is what you call a variable whose value is a process object. But nothing's getting "mixed up".




回答2:


Try using a dictionary mapping Processes to dictionaries containing their information.

proc_dict = {}
for proc in psutil.process_iter():
    try:
        proc_dict[proc] = proc.as_dict(['name', 'pid'])
    except psutil.NoSuchProcess:
        continue

Then sort by the name value of the dictionary for that process.

print(*sorted(proc_dict, lambda x: proc_dict[x]['name']))



回答3:


In the first sample, the lambda function takes some var p and returns p.dict['name']. You could change p here to x or whatever you want: it's just a placeholder.

In the second sample, key=lambda ordem: procs_dic['name'], reverse=False), the lambda takes something called ordem and then only returns procs_dic['name'] over and over again.

The way the key works in sorted is this: as it is iterating over the elements and sorting them, it calls the lambda on every element to determine what value to sort it by.

My guess is that you want the sorted line of code in the 2nd example to look like this:

processes = sorted(procs, key=lambda x: x.name(), reverse=False)

Note that Process.name() returns the name of the process.



来源:https://stackoverflow.com/questions/40428273/python-lambda-function-to-sort-list-according-to-dictionary

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!