Добавление метода в класс после создания класса

Возник следующий вопрос: есть класс, описывающий произвольно заданное электромагнитное поле

class EM_Field():
    
    def __init__(self, E, H):
        self.E = E
        self.H = H

Каким образом можно внутрь этого класса добавить функции, описывающие распределение поля, по типу

def uniform_E(t, x): #однородное поле
    return np.array([1,0,0])

def uniform_H(t, x):
    return np.array([0,1,0])
    
def plane_wave_E_x(t, x, ampl=2, omega=6, phase=0): #плоская волна вдоль Ох
    return np.array([ampl*np.cos(omega*x[0] + phase - omega*t), 0, 0])
      
def plane_wave_H_x(t, x, ampl=1, omega=1, phase=0):
    return np.array([ampl*np.cos(omega*x[0] + phase - omega*t), 0, 0])

чтобы тип поля задавался при инициализации экземпляра класса EM_Field? И чтобы можно было при использовании функции solve_ivp (в частности, при написании правой части уравнения) обращаться к функциям выше как к объекту класса EM_Field?


Ответы (1 шт):

Автор решения: strawdog

Если я не ошибаюсь, добавление метода в существующий класс с аргументами будет работать криво, поскольку класс будет воспринимать первый аргумент как эксплицитную ссылку на экземпляр. Поэтому, вероятно, проще будет воспользоваться библиотекой types:

from types import MethodType
import numpy as np

class EM_Field():   #создаем класс
    def __init__(self, E, H):
        self.E = E
        self.H = H
        
def uniform_E(self, t, x):  #создаем кастомные функции (обратите внимание на self)
    return np.array([1,0,0])

def uniform_H(self, t, x):
    return np.array([0,1,0])    

first_instance = EM_Field(1, 2) # создаем экземпляр класса


first_instance.distr_type = MethodType(uniform_E, first_instance) #добавляем первый метод
# проверка
print(first_instance.distr_type(33,44))
# [1 0 0]
print(first_instance.__dict__)
# {'E': 1, 'H': 2, 'distr_type': <bound method uniform_E of <__main__.EM_Field object at 0x0000020630FA9048>>}

# теперь - второй метод
first_instance.distr_type = MethodType(uniform_H, first_instance)
# проверка:
print(first_instance.distr_type(33,44))
# [0 1 0]
print(first_instance.__dict__)
# {'E': 1, 'H': 2, 'distr_type': <bound method uniform_H of <__main__.EM_Field object at 0x0000020630FA9048>>}
→ Ссылка