Anonymous Quiz
16%
threading
59%
asyncio
11%
multiprocessing
15%
concurrent.futures
❤2👍1
Словарь — это коллекция элементов, которая хранит данные в парах ключ-значение. Ключ в словаре может быть любым неизменяемым типом данных: числами, строками, кортежами. Главное требование к ключу — он должен быть уникальным в рамках одного словаря и хешируемым.
Хешируемость означает, что объект должен иметь хеш-значение, которое не изменяется на протяжении всего времени существования объекта. Это необходимо для того, чтобы Python мог быстро находить значение по ключу. Если бы ключи были изменяемыми, их хеш-значения могли бы измениться, и это привело бы к тому, что значение по ключу стало бы невозможно найти.
my_dict = {"name": "Alice", "age": 25}
my_dict = {1: "one", 2: "two"}
my_dict = {(1, 2): "point", (3, 4): "another point"}
Изменяемые типы данных, такие как списки или другие словари, не могут быть ключами, потому что они не хешируемы.
Ключи в словаре Python — это неизменяемые и хешируемые объекты, такие как строки, числа или кортежи. Это обеспечивает эффективный доступ и хранение данных. В качестве ключей используются данные, которые легко идентифицировать и которые не изменяются во время работы программы.
Please open Telegram to view this post
VIEW IN TELEGRAM
🔥6
Anonymous Quiz
80%
Класс может переопределять методы родительского класса
6%
Наследование в Python не поддерживает множественное наследование
8%
Классы в Python не могут наследовать встроенные типы данных
7%
Класс может наследовать только один другой класс
💊10🤔3👍2❤1
Объектно-ориентированное программирование (ООП) — это парадигма программирования, основанная на концепции "объектов", которые могут содержать данные в виде полей (атрибуты или свойства) и код в виде процедур (методы).
ООП используется для структурирования программы таким образом, чтобы свойства и поведения были собраны в отдельные объекты. Например, в программе для управления животными в зоопарке каждое животное может быть объектом с атрибутами, такими как имя, возраст и вид, а также методами, такими как кормление или игра. Это делает программу легко понимаемой, расширяемой и поддерживаемой.
class Animal:
def __init__(self, name, age):
self.name = name
self.age = age
def speak(self):
return "Звуки, которые издает животное"
class Dog(Animal): # Наследование класса Animal
def speak(self): # Переопределение метода speak
return "Гав"
# Создание объекта класса Dog
my_dog = Dog("Бобик", 5)
print(my_dog.speak()) # Вывод: Гав
В этом примере
Animal
является базовым классом с методом speak
, а Dog
— производным классом, который наследует свойства Animal
и переопределяет метод speak
. Это демонстрирует наследование и полиморфизм.ООП — это метод организации программы с помощью объектов, которые объединяют данные и методы работы с этими данными. Это делает программы более понятными, удобными для разработки и поддержки. Основные принципы ООП включают инкапсуляцию, наследование, полиморфизм и абстракцию.
Please open Telegram to view this post
VIEW IN TELEGRAM
👍3🔥3
Anonymous Quiz
20%
thread.sleep()
29%
thread.join()
16%
thread.hold()
35%
thread.wait()
Лямбда-функции — это небольшие анонимные функции, состоящие из одного выражения, результат которого является значением функции. Они определяются с помощью ключевого слова
lambda
, за которым следуют аргументы функции, двоеточие и выражение, значение которого функция должна вернуть.Лямбда-функции часто используются в тех случаях, когда необходима простая функция для кратковременного использования, и нет смысла определять полноценную функцию с помощью
def
. Это может быть полезно для сортировки или фильтрации данных, а также в качестве аргумента для функций высшего порядка, таких как map()
, filter()
и reduce()
.# Определение лямбда-функции для вычисления квадрата числа
square = lambda x: x * x
# Использование лямбда-функции
print(square(5)) # Выведет 25
# Лямбда-функция в качестве аргумента функции map()
numbers = [1, 2, 3, 4]
squared_numbers = list(map(lambda x: x ** 2, numbers))
print(squared_numbers) # Выведет [1, 4, 9, 16]
# Лямбда-функция для фильтрации списка
even_numbers = list(filter(lambda x: x % 2 == 0, numbers))
print(even_numbers) # Выведет [2, 4]
Лямбда-функции удобны для создания небольших функций на лету, без необходимости явно определять функцию с использованием
def
. Однако стоит отметить, что использование лямбда-функций может сделать код менее читаемым, если выражение становится сложным. По этой причине рекомендуется использовать лямбда-функции для простых операций и переходить к обычному определению функций с def
для более сложной логики.лямбда-функции — это компактный способ создания анонимных функций для выполнения простых выражений. Они особенно полезны для использования в качестве аргументов для функций, работающих с коллекциями данных.
Please open Telegram to view this post
VIEW IN TELEGRAM
👍21
Anonymous Quiz
62%
queue.Queue.put()
12%
set.add()
14%
dict.update()
11%
list.append()
👍2❤1
MRO (Method Resolution Order) — это порядок, в котором Python ищет методы и атрибуты класса при их вызове. Этот порядок особенно важен в контексте множественного наследования, когда класс наследует поведение и атрибуты от нескольких родительских классов, и нужно четко определить, откуда именно брать эти атрибуты и методы в случае их совпадения.
MRO помогает избежать проблемы алмаза (diamond problem), которая возникает, когда два родительских класса наследуют от одного и того же базового класса, а затем эти классы сливаются в один дочерний класс. Без четко определенного MRO Python не смог бы автоматически решить, в каком порядке следует искать методы и атрибуты среди родительских классов.
Python использует алгоритм C3 Linearization для определения MRO. Этот алгоритм гарантирует, что порядок разрешения методов учитывает следующие условия:
Можно узнать MRO любого класса, используя атрибут
__mro__
или метод mro()
у самого класса.class Base:
pass
class A(Base):
pass
class B(Base):
pass
class C(A, B):
pass
print(C.mro())
В этом примере порядок разрешения методов для класса
C
будет следующим: C, A, B,
Base, object
. Это означает, что если метод вызывается для экземпляра класса C
, интерпретатор Python будет искать его сначала в C
, затем в A
, после в B
, затем в Base
и, наконец, в встроенном объекте object
, который является базовым для всех классов.MRO определяет порядок, в котором интерпретатор будет искать методы и атрибуты при их вызове в контексте множественного наследования. Это обеспечивает предсказуемость и избегает конфликтов при наследовании от нескольких классов.
Please open Telegram to view this post
VIEW IN TELEGRAM
👍11❤1
Anonymous Quiz
55%
Протоколы позволяют проверять соответствие объектов во время выполнения
23%
Протоколы требуют явного указания реализации методов
6%
Протоколы ограничивают наследование классов
17%
Протоколы не могут использоваться с абстрактными методами
Миксин (Mixin) – это класс, предназначенный для предоставления определённых методов для использования другими классами, без необходимости становиться родительским классом для этих классов. Главная цель миксина - реализация функциональности, которую можно легко подключить к другому классу. Миксины позволяют разработчикам использовать композицию для добавления функций в классы вместо наследования, что делает структуру кода гибче и модульнее.
Применение миксинов удобно, когда одна и та же функциональность нужна в разных классах, но эти классы не должны быть связаны отношениями наследования. Таким образом, миксины позволяют избежать дублирования кода и упростить его поддержку.
class JsonMixin:
def to_json(self):
import json
return json.dumps(self.__dict__)
class Person:
def __init__(self, name, age):
self.name = name
self.age = age
class PersonJson(JsonMixin, Person): # Использование миксина для добавления функциональности сериализации в JSON
pass
p = PersonJson('Иван', 25)
print(p.to_json()) # Выведет строку в формате JSON, представляющую объект PersonJson
В этом примере
JsonMixin
предоставляет метод to_json
, который может сериализовать объекты класса в JSON. Класс PersonJson
наследует этот метод благодаря множественному наследованию, где JsonMixin
используется для добавления функциональности сериализации к классу Person
, не изменяя его исходный код.Использование миксинов делает код более читаемым и легко поддерживаемым, так как оно позволяет разработчикам комбинировать и переиспользовать функциональности между различными классами без изменения их иерархии наследования.
Миксин - это способ добавления функциональности к классам через множественное наследование, без необходимости изменять их иерархию. Это позволяет сделать код более модульным и легким для поддержки.
Please open Telegram to view this post
VIEW IN TELEGRAM
❤13👍5
Anonymous Quiz
9%
Магические методы вызываются напрямую пользователем
14%
Магические методы не могут быть переопределены
18%
Магические методы всегда должны быть приватными
60%
Магические методы используются для перегрузки операторов и встроенных функций
Существуют три основных типа методов, которые можно определить в классе: методы экземпляра, методы класса и статические методы. Каждый из этих типов методов имеет своё предназначение и способы вызова. Различия между ними заключаются в том, к какому контексту они привязаны (экземпляр, класс или независимость от обоих) и как они объявляются.
Работают с конкретным экземпляром класса и могут изменять состояние этого экземпляра. Они принимают как первый аргумент
self
, который ссылается на текущий экземпляр класса.self
.class MyClass:
def __init__(self, value):
self.value = value
def increment(self):
self.value += 1
# Использование
obj = MyClass(10)
obj.increment()
print(obj.value) # Вывод: 11
Работают с самим классом, а не с его экземплярами. Они принимают как первый аргумент
cls
, который ссылается на сам класс. Методы класса обозначаются декоратором @classmethod
.cls
.class MyClass:
count = 0
def __init__(self):
MyClass.count += 1
@classmethod
def get_count(cls):
return cls.count
# Использование
obj1 = MyClass()
obj2 = MyClass()
print(MyClass.get_count()) # Вывод: 2
Не зависят ни от экземпляра класса, ни от самого класса. Они не принимают
self
или cls
в качестве первого аргумента. Статические методы обозначаются декоратором @staticmethod
.class MyClass:
@staticmethod
def greet(name):
return f"Hello, {name}!"
# Использование
print(MyClass.greet("Alice")) # Вывод: Hello, Alice!
Please open Telegram to view this post
VIEW IN TELEGRAM
🔥7👍5❤1
Anonymous Quiz
11%
Сборка мусора работает только с типами данных, встроенными в Python
81%
Сборка мусора основана на подсчете ссылок и сборке циклических ссылок
2%
Сборка мусора выполняется вручную пользователем
6%
Сборка мусора удаляет объекты сразу после их создания
👍4
Декоратор
@classmethod
используется для определения метода класса, который работает с самим классом, а не с его экземплярами. Методы, определенные с использованием @classmethod
, принимают класс как первый аргумент, что позволяет им взаимодействовать с атрибутами и методами класса, а не конкретных экземпляров.cls
. Это позволяет методу класса получить доступ к атрибутам и методам класса.class MyClass:
count = 0
def __init__(self):
MyClass.count += 1
@classmethod
def get_count(cls):
return cls.count
# Создание объектов класса
obj1 = MyClass()
obj2 = MyClass()
# Вызов метода класса
print(MyClass.get_count()) # Вывод: 2
MyClass
содержит атрибут класса count
, который увеличивается при каждом создании экземпляра.get_count
возвращает текущее значение атрибута count
. Он использует параметр cls
для доступа к атрибуту класса.get_count
вызывается на самом классе MyClass
, а не на экземпляре класса.class Person:
def __init__(self, name, age):
self.name = name
self.age = age
@classmethod
def from_birth_year(cls, name, birth_year):
age = 2023 - birth_year
return cls(name, age)
# Использование
person1 = Person("Alice", 30)
person2 = Person.from_birth_year("Bob", 1993)
print(person1.name, person1.age) # Вывод: Alice 30
print(person2.name, person2.age) # Вывод: Bob 30
from_birth_year
используется для создания экземпляра класса Person
на основе года рождения.from_birth_year
вычисляет возраст и вызывает основной конструктор класса (__init__
) для создания нового экземпляра.Различие между
@classmethod
и @staticmethod
: @classmethod:
Метод получает класс (cls
) как первый аргумент и может изменять состояние класса.@staticmethod:
Метод не получает ни класс, ни экземпляр как первый аргумент и не может изменять состояние класса или экземпляра.class MyClass:
class_attribute = 0
@classmethod
def increment_class_attribute(cls):
cls.class_attribute += 1
@staticmethod
def static_method():
print("This is a static method")
# Использование
MyClass.increment_class_attribute()
print(MyClass.class_attribute) # Вывод: 1
MyClass.static_method() # Вывод: This is a static method
Декоратор
@classmethod
позволяет определять методы, которые работают с самим классом, а не с его экземплярами. Эти методы могут быть полезны для выполнения операций на уровне класса, таких как создание новых экземпляров с использованием альтернативных конструкторов или изменение атрибутов класса. Понимание различий между методами класса, статическими методами и методами экземпляра помогает эффективно использовать объектно-ориентированные возможности.Please open Telegram to view this post
VIEW IN TELEGRAM
👍8❤1
Anonymous Quiz
29%
asynccontext.local()
11%
threading.local()
21%
contextvars.ContextVar()
39%
asyncio.Local()
👾3
Декоратор
@staticmethod
используется для определения статических методов внутри класса. Статические методы не зависят от экземпляра класса или самого класса. Они ведут себя как обычные функции, но их логически объединяют в класс для удобства и организации кода. Статические методы не принимают ни self
, ни cls
в качестве первого аргумента.self
), ни класс (cls
) как первый аргумент.class MathOperations:
@staticmethod
def add(x, y):
return x + y
@staticmethod
def subtract(x, y):
return x - y
# Использование
print(MathOperations.add(5, 3)) # Вывод: 8
print(MathOperations.subtract(5, 3)) # Вывод: 2
@staticmethod
и @classmethod
:cls
), ни экземпляр (self
) в качестве аргумента.
@classmethod:
cls
) в качестве первого аргумента.class MyClass:
class_attribute = 0
@classmethod
def increment_class_attribute(cls):
cls.class_attribute += 1
@staticmethod
def static_method():
return "This is a static method"
# Использование методов класса и статических методов
MyClass.increment_class_attribute()
print(MyClass.class_attribute) # Вывод: 1
print(MyClass.static_method()) # Вывод: This is a static method
from datetime import date
class DateUtil:
@staticmethod
def is_weekend(d):
return d.weekday() >= 5
@staticmethod
def days_between(d1, d2):
return abs((d2 - d1).days)
# Использование
today = date.today()
future_date = date(2023, 12, 31)
print(DateUtil.is_weekend(today)) # Вывод: True или False в зависимости от текущего дня недели
print(DateUtil.days_between(today, future_date)) # Вывод: Количество дней между сегодня и 31 декабря 2023 года
Декоратор
@staticmethod
позволяет определять методы, которые не зависят от состояния экземпляра или класса. Эти методы используются для логической организации утилитарных функций, которые связаны с классом по смыслу, но не требуют доступа к его состоянию. Понимание различий между статическими методами и методами класса помогает правильно организовывать код и выбирать подходящий тип метода для конкретной задачи.Please open Telegram to view this post
VIEW IN TELEGRAM
👍5❤1
Anonymous Quiz
5%
asyncio.Task
72%
multiprocessing.Process
8%
concurrent.futures.ThreadPoolExecutor
15%
threading.Thread
Декоратор
@dataclass
, используется для автоматического создания методов для классов, которые в основном используются для хранения данных. Он автоматически генерирует такие методы, как __init__
, repr, eq, и другие, на основе аннотаций типов, предоставленных в классе. Это делает код более лаконичным и менее подверженным ошибкам, устраняя необходимость вручную писать эти методы для простых классов данных.from dataclasses import dataclass
@dataclass
class Person:
name: str
age: int
# Использование
p1 = Person(name="Alice", age=30)
p2 = Person(name="Bob", age=25)
print(p1) # Вывод: Person(name='Alice', age=30)
print(p2) # Вывод: Person(name='Bob', age=25)
@dataclass
автоматически генерирует конструктор init, метод repr и метод eq на основе аннотаций типов.@dataclass
class Person:
name: str
age: int = 0
p1 = Person(name="Alice")
print(p1) # Вывод: Person(name='Alice', age=0)
field:
Для более тонкой настройки можно использовать функцию field
из модуля dataclasses
.from dataclasses import dataclass, field
@dataclass
class Person:
name: str
age: int = field(default=0, metadata={"info": "Age of the person"})
p1 = Person(name="Alice")
print(p1) # Вывод: Person(name='Alice', age=0)
from dataclasses import dataclass, field
@dataclass
class Person:
name: str
age: int = field(compare=False)
p1 = Person(name="Alice", age=30)
p2 = Person(name="Alice", age=25)
print(p1 == p2) # Вывод: True
from dataclasses import dataclass, field
@dataclass
class Person:
name: str
age: int = field(init=False)
p1 = Person(name="Alice")
p1.age = 30
print(p1) # Вывод: Person(name='Alice')
from dataclasses import dataclass, field
from typing import List
@dataclass
class Person:
name: str
age: int = 0
hobbies: List[str] = field(default_factory=list, compare=False)
p1 = Person(name="Alice", hobbies=["reading", "hiking"])
p2 = Person(name="Alice", age=25, hobbies=["reading", "hiking"])
print(p1) # Вывод: Person(name='Alice', age=0, hobbies=['reading', 'hiking'])
print(p2) # Вывод: Person(name='Alice', age=25, hobbies=['reading', 'hiking'])
print(p1 == p2) # Вывод: True (потому что hobbies не участвуют в сравнении)
Декоратор
@dataclass
значительно упрощает создание классов, предназначенных для хранения данных, автоматизируя создание конструкторов и других методов. Он уменьшает количество шаблонного кода, улучшает читаемость и упрощает поддержку кода. Использование @dataclass
особенно полезно в ситуациях, когда нужно создавать много классов данных с аналогичной структурой и поведением.Please open Telegram to view this post
VIEW IN TELEGRAM
👍14
Anonymous Quiz
22%
threading.get_threads()
8%
threading.enumerate()
27%
threading.count()
43%
threading.active_count()
Атрибуты класса и атрибуты объекта (также известные как атрибуты экземпляра) играют важную роль. Понимание различий между ними помогает правильно организовать данные и поведение в классе.
Это переменная, которая определяется внутри класса и доступна для всех экземпляров этого класса. Разделяется всеми экземплярами класса, и изменение атрибута класса отражается на всех экземплярах.
class MyClass:
class_attribute = 42 # Атрибут класса
# Доступ к атрибуту класса через класс
print(MyClass.class_attribute) # Вывод: 42
# Создание экземпляров
obj1 = MyClass()
obj2 = MyClass()
# Доступ к атрибуту класса через экземпляры
print(obj1.class_attribute) # Вывод: 42
print(obj2.class_attribute) # Вывод: 42
# Изменение атрибута класса
MyClass.class_attribute = 100
print(obj1.class_attribute) # Вывод: 100
print(obj2.class_attribute) # Вывод: 100
Это переменная, которая определяется внутри метода конструктора (
__init__
) или другого метода и принадлежит конкретному экземпляру класса. Каждый экземпляр имеет свои собственные копии атрибутов объекта.class MyClass:
def __init__(self, value):
self.instance_attribute = value # Атрибут объекта
# Создание экземпляров с разными атрибутами объекта
obj1 = MyClass(10)
obj2 = MyClass(20)
# Доступ к атрибутам объекта через экземпляры
print(obj1.instance_attribute) # Вывод: 10
print(obj2.instance_attribute) # Вывод: 20
# Изменение атрибута объекта
obj1.instance_attribute = 30
print(obj1.instance_attribute) # Вывод: 30
print(obj2.instance_attribute) # Вывод: 20
__init__
) или других методах экземпляра.Используется для хранения данных, общих для всех экземпляров класса, например, счетчиков, настроек по умолчанию.
class MyClass:
instance_count = 0 # Атрибут класса
def __init__(self):
MyClass.instance_count += 1
# Создание экземпляров
obj1 = MyClass()
obj2 = MyClass()
print(MyClass.instance_count) # Вывод: 2
class MyClass:
def __init__(self, name):
self.name = name # Атрибут объекта
# Создание экземпляров с уникальными данными
obj1 = MyClass("Alice")
obj2 = MyClass("Bob")
print(obj1.name) # Вывод: Alice
print(obj2.name) # Вывод: Bob
Атрибуты класса и атрибуты объекта играют важные роли в организации данных в классах. Атрибуты класса используются для хранения данных, общих для всех экземпляров класса, тогда как атрибуты объекта предназначены для уникальных данных каждого экземпляра. Понимание этих различий помогает правильно организовать данные и поведение в классах и эффективно использовать объектно-ориентированное программирование.
Please open Telegram to view this post
VIEW IN TELEGRAM
❤2👍2💊2