Как создать уникальное значение для каждого ключа с помощью dict.fromkeys?

Во-первых, я новичок в Python, поэтому прошу прощения, если я что-то упустил, но я бы хотел использовать dict.fromkeys (или что-то подобное) для создания словаря списков, ключи которого приведены в другой список. Я выполняю некоторые тесты времени, и я бы хотел, чтобы ключ был входной переменной, а список содержал время для прогонов:

def benchmark(input):
    ...
    return time_taken

runs = 10
inputs = (1, 2, 3, 5, 8, 13, 21, 34, 55)
results = dict.fromkeys(inputs, [])

for run in range(0, runs):
    for i in inputs:
        results[i].append(benchmark(i))

Проблема, с которой я сталкиваюсь, заключается в том, что все ключи в словаре, похоже, имеют один и тот же список, и каждый запуск просто добавляется к нему. Есть ли способ создать уникальный пустой список для каждого ключа с помощью fromkeys? Если нет, есть ли другой способ сделать это без генерации результирующего словаря вручную?

Ответ 1

Проблема заключается в том, что в

results = dict.fromkeys(inputs, [])

[] оценивается только один раз, прямо там.

Я бы переписал этот код следующим образом:

runs = 10
inputs = (1, 2, 3, 5, 8, 13, 21, 34, 55)
results = {}

for run in range(runs):
    for i in inputs:
        results.setdefault(i,[]).append(benchmark(i))

Другой вариант:

runs = 10
inputs = (1, 2, 3, 5, 8, 13, 21, 34, 55)
results = dict([(i,[]) for i in inputs])

for run in range(runs):
    for i in inputs:
        results[i].append(benchmark(i))

Ответ 2

Отъезд defaultdict (требуется Python 2.5 или выше).

from collections import defaultdict

def benchmark(input):
    ...
    return time_taken

runs = 10
inputs = (1, 2, 3, 5, 8, 13, 21, 34, 55)
results = defaultdict(list) # Creates a dict where the default value for any key is an empty list

for run in range(0, runs):
    for i in inputs:
        results[i].append(benchmark(i))

Ответ 3

Вы также можете сделать это, если не хотите узнать что-нибудь новое (хотя я рекомендую вам это делать!) Мне любопытно, какой метод быстрее?

results = dict.fromkeys(inputs)

for run in range(0, runs):
    for i in inputs:
        if not results[i]:
            results[i] = []
        results[i].append(benchmark(i))