python
September 6, 2024

Словари в Python

Словари (dict) в Python — это неупорядоченная коллекция, которая хранит данные в парах ключ-значение. Создавая словарь, мы передаем последовательность элементов внутрь фигурных скобок {}, разделяя их запятыми (,). Каждый элемент имеет ключ и значение, выраженное парой «ключ: значение».

Наглядно синтаксис словарей выглядит следующим образом:

items_dict = {"vehicle": "Tesla", "fruit": "apple", "lucky_number": 7}

Вот ещё один пример словаря, где ключами являются числа, а значениями — строки:

gender_dict = {0: 'woman',
               1: 'man'}

Как видно из примеров, для создания словаря можно перечислить в фигурных скобках пары: ключ и значение. Ключ и значение отделяются двоеточием и пробелами, а пары перечисляются через запятую.

Другой способ создать словарь - это использовать функцию dict().

empty_dict = dict()

Функция dict() создаст словарь, инициализированный из необязательного позиционного аргумента и возможно пустого набора ключевых аргументов.

Параметры:

  • kwarg - ключевые аргументы one=1, two=2, three=3
  • iterable - итерируемый объект, например список следующего вида [('one', 1), ('two', 2), ('three', 3)]
  • mapping - словарь, например {'three': 3, 'two': 2, 'one': 1}

Если позиционный аргумент не задан, создается пустой словарь, как в примере выше.

Примеры использования функции dict:

# создание словаря с помощью ключевых аргументов
dict_sample = dict(one=1, two=2, three=3)
print(dict_sample) # {'one': 1, 'two': 2, 'three': 3}

# создание словаря с помощью другого словаря
dict_sample = dict({0: 'orange', 1: 'pawpaw'})
print(dict_sample) # {0: 'orange', 1: 'pawpaw'}

# создание словаря с помощью последовательности
dict_sample = dict([(0,'apple'), (1,'pawpaw')])
print(dict_sample) # {0: 'apple', 1: 'pawpaw'}
Личная рекомендация: Для большинства случаев следует использовать фигурные скобки {} для создания пустого словаря из-за их более высокой производительности и лучшей читаемости кода. Использование функции dict() может быть оправдано в специфических случаях, например, при создании словаря с определёнными параметрами или в контексте более сложных выражений.

Важно отметить некоторые особенности словарей:

  1. Ключом в словаре может быть только неизменяемый тип данных (например, строка, число или кортеж).
  2. Значением может быть любой тип данных, включая другие словари или списки.
В первом пункте, есть небольшая неточность. Дело в том, что ключи в словарях должны быть хешируемыми. Это означает, что они должны иметь неизменяемое хэш-значение, что гарантирует их уникальность и неизменность в контексте словаря. Однако подобные тонкости будут рассмотрены более подробно в другой статье.

В отличие от списков, где для получения элементов необходимо обращаться к ним по числовому индексу, в словарях мы обращаемся к элементам по ключу. Это дает больше гибкости и удобства при работе с данными.

Для получения значения в словаре, необходимо указать ключ в квадратных скобках после имени словаря:

items_dict = {"vehicle": "Tesla", "fruit": "apple", "lucky_number": 7}
print(items_dict["vehicle"])

Выведет:

Tesla

При попытке получить значение по несуществующему ключу вызывается исключение KeyError

items_dict = {"vehicle": "Tesla", "fruit": "apple", "lucky_number": 7}

print(items_dict["test"])

В качестве результата получим следующее сообщение:

print(items_dict["test"])
      ~~~~~~~~~~^^^^^^
KeyError: 'test'

Как получить элементы списка без ошибок?

Первый способ избежать подобной ошибки. Это использовать уже известный нам оператора in.

При помощи него мы можем проверить, существует ли ключ в словаре:

items_dict = {"vehicle": "Tesla", "fruit": "apple", "lucky_number": 7}

print("vehicle" in items_dict)
print("qwerty" in items_dict)
print("123" in items_dict)

Выведет:

True
False
False

Второй способ. Использование специального метода get(key[, default])

Этот метод возвращает значение для ключа, если ключ находится в словаре, иначе возвращает значение по умолчанию default. Если значение по умолчанию не задано, метод возвращает None (но никогда не возвращает исключение).

Добавление и изменение содержимого словаря

Добавление новых пар в словарь происходит достаточно просто:

temp_dict = {}
temp_dict["key"] = "value"
print(temp_dict)

в результате получим:

{"key": "value"}

Изменение выполняется абсолютно также:

temp_dict = {"key": "value"} 
temp_dict["key"] = "new_value" 
print(temp_dict["key"])

Вывод программы:

new_value

Обратите внимание, при записи значения по уже существующему ключу он создаётся заново с новым значением, а прошлый стирается

Для добавления/изменения сразу нескольких объектов в словаре, используется специальный метод update([other]). Он обновляет словарь парами ключ-значение из other, перезаписывая существующие ключи.

В дальнейших примерах мы будем использовать следующий словарь, содержащий в себе информацию о студентах:

students = {
    'Alice': {'age': 22, 'major': 'Computer Science'},
    'Bob': {'age': 21, 'major': 'Mathematics'}
}

Пример 1: Добавление нового студента

new_student = {'Charlie': {'age': 23, 'major': 'Physics'}}
students.update(new_student)

print(students)

Получим:

{'Alice': {'age': 22, 'major': 'Computer Science'}, 'Bob': {'age': 21, 'major': 'Mathematics'}, 'Charlie': {'age': 23, 'major': 'Physics'}}

Пример 2: Обновление информации о существующем студенте

update_info = {'Bob': {'age': 22, 'major': 'Data Science'}}
students.update(update_info)

print(students)

Получим:

{'Alice': {'age': 22, 'major': 'Computer Science'}, 'Bob': {'age': 22, 'major': 'Data Science'}, 'Charlie': {'age': 23, 'major': 'Physics'}}

Пример 3: Добавление нового студента и обновление информации о другом с помощью ключевых аргументов

students.update({'David': {'age': 24, 'major': 'Biology'}}, Alice={'age': 23, 'major': 'Artificial Intelligence'})

print(students)

Получим:

{'Alice': {'age': 23, 'major': 'Artificial Intelligence'}, 'Bob': {'age': 22, 'major': 'Data Science'}, 'Charlie': {'age': 23, 'major': 'Physics'}, 'David': {'age': 24, 'major': 'Biology'}}

Пример 4: Обновление словаря с помощью итерируемого объекта

students.update([('Eve', {'age': 25, 'major': 'Chemistry'}), ('Charlie', {'age': 24, 'major': 'Quantum Physics'})])

print(students)

Получим:

{'Alice': {'age': 23, 'major': 'Artificial Intelligence'}, 'Bob': {'age': 22, 'major': 'Data Science'}, 'Charlie': {'age': 24, 'major': 'Quantum Physics'}, 'David': {'age': 24, 'major': 'Biology'}, 'Eve': {'age': 25, 'major': 'Chemistry'}}

Пример 5: Обновление словаря с помощью другого словаря, содержащего вложенные словари

new_data = {
    'Alice': {'age': 24, 'major': 'Machine Learning'},
    'Frank': {'age': 26, 'major': 'Economics'}
}
students.update(new_data)

print(students)

Результат:

{'Alice': {'age': 24, 'major': 'Machine Learning'}, 'Bob': {'age': 22, 'major': 'Data Science'}, 'Charlie': {'age': 24, 'major': 'Quantum Physics'}, 'David': {'age': 24, 'major': 'Biology'}, 'Eve': {'age': 25, 'major': 'Chemistry'}, 'Frank': {'age': 26, 'major': 'Economics'}}

Удаление элементов из словаря

Для удаления элемента из словаря можно использовать либо оператор del dict[key], либо метод dict.pop(key[, default]). В первом случае из словаря удаляется соответствующая пара. Или, если такого ключа нет, возвращается KeyError.

Пример 1: Использование del для удаления элемента

temp_dict = {"key": "value"}

# Удаляем элемент с ключом "key"
del temp_dict["key"]
print(f"temp_dict = {temp_dict}")

# Удаляем элемент с несуществующим ключом
del temp_dict["python"]

Результат:

temp_dict = {}
Traceback (most recent call last): 
  File "", line 1, in 
KeyError: 'python'

Метод dict.pop(key[, default]) удаляет из словаря элемент с заданным ключом и возвращает его значение. Если ключ отсутствует, метод возвращает значение default . Если значение default не задано и ключа не существует, метод pop() вызовет исключение KeyError.

Пример 2: Использование dict.pop(key[, default]) для удаления элемента

temp_dict = {"key": "value"}

deleted_value = temp_dict.pop("key")

print(f"Удаленное значение: {deleted_value}")
print(f"temp_dict = {temp_dict}\n")

deleted_value = temp_dict.pop("non_existent_key", "default_value")

print(f"Возвращенное значение: {deleted_value}")
print(f"temp_dict = {temp_dict}")

Результат:

Удаленное значение: value
temp_dict = {}

Возвращенное значение: default_value
temp_dict = {'key': 'value'}

Пример 3: Использование dict.pop(key[, default]) с отсутствующим ключом без значения по умолчанию

temp_dict = {"key": "value"}

value = temp_dict.pop("non_existent_key")

print(f"temp_dict = {temp_dict}")

Результат:

Traceback (most recent call last):
  File "", line 4, in <module>
    value = temp_dict.pop("non_existent_key")
            ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
KeyError: 'non_existent_key'

Методы словарей

Словари в Python имеют множество различных полезных методов, которые помогут вам в работе с ними. C некоторыми из них вы уже успели познакомиться. Всё повторим и разберемся с неизученными :).

1. copy()

Сигнатура:

dict.copy()

Описание:
Этот метод возвращает поверхностную копию словаря. Мы должны быть осторожны с такими копиями: если словарь содержит списки, кортежи или множества, то в созданной копии будут только ссылки на объекты из оригинала.

Пример:

dict1 = {'car': 'машина', 'apple': 'яблоко', 'orange': 'апельсин'}
dict2 = dict1.copy()
print(dict2)  # Выведет {'car': 'машина', 'apple': 'яблоко', 'orange': 'апельсин'}

При использовании метода copy() для создания копии словаря, если словарь содержит списки, кортежи, множества или другие словари, то в созданной копии будут только ссылки на объекты из оригинала. Это означает, что изменения во вложенных объектах в копии будут отражаться и в оригинале.

Пример:

import copy

# Исходный словарь с вложенными списками
original_dict = {
    'a': [1, 2, 3],
    'b': (4, 5, 6),
    'c': {7, 8, 9}
}

# Создаем поверхностную копию
shallow_copy = original_dict.copy()

# Изменяем вложенный список в поверхностной копии
shallow_copy['a'].append(4)

# Выводим оригинальный словарь и поверхностную копию
print("Оригинальный словарь:", original_dict)
print("Поверхностная копия:", shallow_copy)

Результат:

Оригинальный словарь: {'a': [1, 2, 3, 4], 'b': (4, 5, 6), 'c': {8, 9, 7}}
Поверхностная копия: {'a': [1, 2, 3, 4], 'b': (4, 5, 6), 'c': {8, 9, 7}}

Как видно из результата, изменения во вложенном списке в поверхностной копии отразились и в оригинале.

Чтобы избежать этой проблемы, можно создать глубокую копию словаря, используя функцию copy.deepcopy(x). Глубокая копия создает независимую копию всех вложенных объектов.

Пример:

import copy

# Исходный словарь с вложенными списками
original_dict = {
    'a': [1, 2, 3],
    'b': (4, 5, 6),
    'c': {7, 8, 9}
}

# Создаем глубокую копию
deep_copy = copy.deepcopy(original_dict)

# Изменяем вложенный список в глубокой копии
deep_copy['a'].append(4)

# Выводим оригинальный словарь и глубокую копию
print("Оригинальный словарь:", original_dict)
print("Глубокая копия:", deep_copy)

Результат:

Оригинальный словарь: {'a': [1, 2, 3], 'b': (4, 5, 6), 'c': {8, 9, 7}}
Глубокая копия: {'a': [1, 2, 3, 4], 'b': (4, 5, 6), 'c': {8, 9, 7}}

Теперь изменения во вложенном списке в глубокой копии не отражаются в оригинале, так как глубокая копия создает независимую копию всех вложенных объектов.

Пояснения:

  • Поверхностная копия: Создает копию словаря, но вложенные объекты (списки, кортежи, множества) остаются ссылками на оригинальные объекты.
  • Глубокая копия: Создает полностью независимую копию словаря, включая все вложенные объекты.

Использование глубокой копии позволяет избежать нежелательных побочных эффектов при работе с вложенными структурами данных.

2. get(key[, default])

Синтаксис:

dict.get(key[, default])

Описание:
Возвращает значение по указанному ключу. Если ключ отсутствует, возвращает значение default (по умолчанию None).

Пример:

dict1 = {'car': 'машина', 'apple': 'яблоко', 'orange': 'апельсин'}
print(dict1.get('car'))  # Выведет 'машина'
print(dict1.get('home', 'дом'))  # Выведет 'дом', так как ключ 'home' отсутствует

3. clear()

Синтаксис:

dict.clear()

Описание:
Удаляет все элементы из словаря.

Пример:

dict1 = {'car': 'машина', 'apple': 'яблоко', 'orange': 'апельсин'}
dict1.clear()
print(dict1)  # Выведет {}

4. keys()

Синтаксис:

dict.keys()

Описание:
Возвращает объект представления, содержащий все ключи словаря.

Пример:

dict1 = {'car': 'машина', 'apple': 'яблоко', 'orange': 'апельсин'}
print(dict1.keys())  # Выведет dict_keys(['car', 'apple', 'orange'])

5. values()

Синтаксис:

dict.values()

Описание:
Возвращает объект представления, содержащий все значения словаря.

Пример:

dict1 = {'car': 'машина', 'apple': 'яблоко', 'orange': 'апельсин'}
print(dict1.values())  # Выведет dict_values(['машина', 'яблоко', 'апельсин'])

6. items()

Синтаксис:

dict.items()

Описание:
Возвращает объект представления, содержащий пары ключ-значение в виде кортежей.

Пример:

dict1 = {'car': 'машина', 'apple': 'яблоко', 'orange': 'апельсин'}
print(dict1.items())  # Выведет dict_items([('car', 'машина'), ('apple', 'яблоко'), ('orange', 'апельсин')])

7. pop(key[, default])

Синтаксис:

dict.pop(key[, default])

Описание:
Удаляет элемент с указанным ключом и возвращает его значение. Если ключ отсутствует, возвращает значение default (если оно указано) или вызывает исключение KeyError.

Пример:

dict1 = {'car': 'машина', 'apple': 'яблоко', 'orange': 'апельсин'}
print(dict1.pop('car'))  # Выведет 'машина'
print(dict1.pop('home', 'дом'))  # Выведет 'дом', так как ключ 'home' отсутствует
print(dict1)  # Выведет {'apple': 'яблоко', 'orange': 'апельсин'}

8. popitem()

Синтаксис:

dict.popitem()

Описание:
Удаляет и возвращает последнюю добавленную пару ключ-значение в виде кортежа. Если словарь пуст, метод вызывает исключение KeyError.

Пример:

dict1 = {'car': 'машина', 'apple': 'яблоко', 'orange': 'апельсин'}
print(dict1.popitem())  # Выведет ('orange', 'апельсин')
print(dict1)  # Выведет {'car': 'машина', 'apple': 'яблоко'}

9. setdefault(key[, default])

Синтаксис:

dict.setdefault(key[, default])

Описание:
Возвращает значение по указанному ключу. Если ключ отсутствует, метод добавляет его в словарь со значением default (по умолчанию None).

Пример:

dict1 = {'car': 'машина', 'apple': 'яблоко', 'orange': 'апельсин'}
print(dict1.setdefault('car'))  # Выведет 'машина'
print(dict1.setdefault('home', 'дом'))  # Выведет 'дом'
print(dict1)  # Выведет {'car': 'машина', 'apple': 'яблоко', 'orange': 'апельсин', 'home': 'дом'}

10. update([other])

Синтаксис:

dict.update([other])

Описание:
Обновляет словарь, добавляя пары ключ-значение из другого словаря или итерируемого объекта. Существующие ключи перезаписываются новыми значениями.

Пример:

dict1 = {'car': 'машина', 'apple': 'яблоко', 'orange': 'апельсин'}
dict1.update({'car': 'автомобиль', 'home': 'дом'})
print(dict1)  # Выведет {'car': 'автомобиль', 'apple': 'яблоко', 'orange': 'апельсин', 'home': 'дом'}

На этом данная статья заканчивается, благодарю вас за внимание! Если у вас остались вопросы, смело задавайте их в нашем телеграмм канале!