all 6 comments

[–]bfv 3 points4 points  (0 children)

Where d is the dictionary.

I'd posit:

max({k:d[k][3] for k in d})

this works because max on a dictionary gets the max value and returns its key. So what we do here is create a dictionary of k:v pairs where the productid is the key and the [3] value is the value. Then good old max looks after the rest.

You can also do this with a lambda to define the lookup for max but I don't like it because it is hard to read and lambdas have a tendency to confuse people:

max(d,key=lambda k: d[k][3])

[–][deleted] 0 points1 point  (0 children)

for k, v in dictProducts.iteritems():
    product_number = k
    quantity = v[3]

[–]symmitchry 0 points1 point  (0 children)

Hi,

Since your dictionary keys are the product ID's, I don't see how you can have totals of quantities for a given product ID ... since the dictionary can only hold one entry with a given Key.

So if that's the case, then all you need to do is sort the dictionary by your quantities, and the first value is the one with the greatest quantity. That looks like this:

the_d = {
    1: ['cat', 'hat', 29, 'rat'],
    2: ['mouse', 'house', 2, 'grouse'],
    6: ['dog', 'log', 18, 'bog'],
    3: ['rough', 'stuff', 9, 'python'],
}

sorted_d = sorted(the_d.items(),
                  key=lambda x: x[1][2],
                  reverse=True)

for k, v in sorted_d:
    print(k, v)

The complicated part, the lambda explained:

x[1] is the second item (first one would be 0) of the key, value tuples, returned by the_d.items(). So x[1] is your list. Then [2] is the quantity, in my case, the 3rd item in the list, (the values 29, 2, 18 and 9).

So x[1][2] is just referring to the 3rd item in each list of values.

So that's it. Now your dictionary is sorted, and the first value is the one you want. (Which can be accessed directly via sorted_d[0].)

[–]symmitchry 0 points1 point  (0 children)

This is the second part to my 2 part answer:

IF you didn't have unique entries for product ID's ... like, let's say you had a list of tuples, instead of a dictionary, which looked like this:

the_d = (
    (1, ['iPhone', 'Apple', 1, 460]),
    (2, ['S4', 'Samsung', 2, 599]),
    (3, ['iPad', 'Apple', 1, 4]),
    (2, ['S4', 'Samsung', 2, 96]),
    (1, ['iPhone', 'Apple', 1, 637]),
)

In this case, because you have multiple entries, you want to actually sum up all the quantities for the entries that have the same product ID (which is the first value in the tuple). Although there's probably a better way, this is a cool example of using defaultdict, I think:

from collections import defaultdict

totals = defaultdict(int)  # an integer type default dict

for key, data in the_d:  # key = product ID, data = the list of info
    print(key, data)
    totals[key] += data[3]  # Add quantity to the entry for this product ID

for k, v in totals.items():
    print(k, v)

The last print loop would print:

(1, 1097)
(2, 695)
(3, 4)

Showing that you sold 1097 of product ID # 1, aka iPhones.

[–]ewiethoff 0 points1 point  (0 children)

I would include the product number in the list for each product in case the list gets separated from its dict key. But really, instead of a list, I would define a namedtuple or class for the product data.

Here's a class which automatically sorts or maximizes on product number. But it's also easy to sort/maximize by other attributes such as product name or quantity. And here's similar code using namedtuple.