| """ |
| **Contains** |
| |
| * Medium |
| """ |
| from sympy.physics.units import second, meter, kilogram, ampere |
|
|
| __all__ = ['Medium'] |
|
|
| from sympy.core.basic import Basic |
| from sympy.core.symbol import Str |
| from sympy.core.sympify import _sympify |
| from sympy.functions.elementary.miscellaneous import sqrt |
| from sympy.physics.units import speed_of_light, u0, e0 |
|
|
|
|
| c = speed_of_light.convert_to(meter/second) |
| _e0mksa = e0.convert_to(ampere**2*second**4/(kilogram*meter**3)) |
| _u0mksa = u0.convert_to(meter*kilogram/(ampere**2*second**2)) |
|
|
|
|
| class Medium(Basic): |
|
|
| """ |
| This class represents an optical medium. The prime reason to implement this is |
| to facilitate refraction, Fermat's principle, etc. |
| |
| Explanation |
| =========== |
| |
| An optical medium is a material through which electromagnetic waves propagate. |
| The permittivity and permeability of the medium define how electromagnetic |
| waves propagate in it. |
| |
| |
| Parameters |
| ========== |
| |
| name: string |
| The display name of the Medium. |
| |
| permittivity: Sympifyable |
| Electric permittivity of the space. |
| |
| permeability: Sympifyable |
| Magnetic permeability of the space. |
| |
| n: Sympifyable |
| Index of refraction of the medium. |
| |
| |
| Examples |
| ======== |
| |
| >>> from sympy.abc import epsilon, mu |
| >>> from sympy.physics.optics import Medium |
| >>> m1 = Medium('m1') |
| >>> m2 = Medium('m2', epsilon, mu) |
| >>> m1.intrinsic_impedance |
| 149896229*pi*kilogram*meter**2/(1250000*ampere**2*second**3) |
| >>> m2.refractive_index |
| 299792458*meter*sqrt(epsilon*mu)/second |
| |
| |
| References |
| ========== |
| |
| .. [1] https://en.wikipedia.org/wiki/Optical_medium |
| |
| """ |
|
|
| def __new__(cls, name, permittivity=None, permeability=None, n=None): |
| if not isinstance(name, Str): |
| name = Str(name) |
|
|
| permittivity = _sympify(permittivity) if permittivity is not None else permittivity |
| permeability = _sympify(permeability) if permeability is not None else permeability |
| n = _sympify(n) if n is not None else n |
|
|
| if n is not None: |
| if permittivity is not None and permeability is None: |
| permeability = n**2/(c**2*permittivity) |
| return MediumPP(name, permittivity, permeability) |
| elif permeability is not None and permittivity is None: |
| permittivity = n**2/(c**2*permeability) |
| return MediumPP(name, permittivity, permeability) |
| elif permittivity is not None and permittivity is not None: |
| raise ValueError("Specifying all of permittivity, permeability, and n is not allowed") |
| else: |
| return MediumN(name, n) |
| elif permittivity is not None and permeability is not None: |
| return MediumPP(name, permittivity, permeability) |
| elif permittivity is None and permeability is None: |
| return MediumPP(name, _e0mksa, _u0mksa) |
| else: |
| raise ValueError("Arguments are underspecified. Either specify n or any two of permittivity, " |
| "permeability, and n") |
|
|
| @property |
| def name(self): |
| return self.args[0] |
|
|
| @property |
| def speed(self): |
| """ |
| Returns speed of the electromagnetic wave travelling in the medium. |
| |
| Examples |
| ======== |
| |
| >>> from sympy.physics.optics import Medium |
| >>> m = Medium('m') |
| >>> m.speed |
| 299792458*meter/second |
| >>> m2 = Medium('m2', n=1) |
| >>> m.speed == m2.speed |
| True |
| |
| """ |
| return c / self.n |
|
|
| @property |
| def refractive_index(self): |
| """ |
| Returns refractive index of the medium. |
| |
| Examples |
| ======== |
| |
| >>> from sympy.physics.optics import Medium |
| >>> m = Medium('m') |
| >>> m.refractive_index |
| 1 |
| |
| """ |
| return (c/self.speed) |
|
|
|
|
| class MediumN(Medium): |
|
|
| """ |
| Represents an optical medium for which only the refractive index is known. |
| Useful for simple ray optics. |
| |
| This class should never be instantiated directly. |
| Instead it should be instantiated indirectly by instantiating Medium with |
| only n specified. |
| |
| Examples |
| ======== |
| >>> from sympy.physics.optics import Medium |
| >>> m = Medium('m', n=2) |
| >>> m |
| MediumN(Str('m'), 2) |
| """ |
|
|
| def __new__(cls, name, n): |
| obj = super(Medium, cls).__new__(cls, name, n) |
| return obj |
|
|
| @property |
| def n(self): |
| return self.args[1] |
|
|
|
|
| class MediumPP(Medium): |
| """ |
| Represents an optical medium for which the permittivity and permeability are known. |
| |
| This class should never be instantiated directly. Instead it should be |
| instantiated indirectly by instantiating Medium with any two of |
| permittivity, permeability, and n specified, or by not specifying any |
| of permittivity, permeability, or n, in which case default values for |
| permittivity and permeability will be used. |
| |
| Examples |
| ======== |
| >>> from sympy.physics.optics import Medium |
| >>> from sympy.abc import epsilon, mu |
| >>> m1 = Medium('m1', permittivity=epsilon, permeability=mu) |
| >>> m1 |
| MediumPP(Str('m1'), epsilon, mu) |
| >>> m2 = Medium('m2') |
| >>> m2 |
| MediumPP(Str('m2'), 625000*ampere**2*second**4/(22468879468420441*pi*kilogram*meter**3), pi*kilogram*meter/(2500000*ampere**2*second**2)) |
| """ |
|
|
|
|
| def __new__(cls, name, permittivity, permeability): |
| obj = super(Medium, cls).__new__(cls, name, permittivity, permeability) |
| return obj |
|
|
| @property |
| def intrinsic_impedance(self): |
| """ |
| Returns intrinsic impedance of the medium. |
| |
| Explanation |
| =========== |
| |
| The intrinsic impedance of a medium is the ratio of the |
| transverse components of the electric and magnetic fields |
| of the electromagnetic wave travelling in the medium. |
| In a region with no electrical conductivity it simplifies |
| to the square root of ratio of magnetic permeability to |
| electric permittivity. |
| |
| Examples |
| ======== |
| |
| >>> from sympy.physics.optics import Medium |
| >>> m = Medium('m') |
| >>> m.intrinsic_impedance |
| 149896229*pi*kilogram*meter**2/(1250000*ampere**2*second**3) |
| |
| """ |
| return sqrt(self.permeability / self.permittivity) |
|
|
| @property |
| def permittivity(self): |
| """ |
| Returns electric permittivity of the medium. |
| |
| Examples |
| ======== |
| |
| >>> from sympy.physics.optics import Medium |
| >>> m = Medium('m') |
| >>> m.permittivity |
| 625000*ampere**2*second**4/(22468879468420441*pi*kilogram*meter**3) |
| |
| """ |
| return self.args[1] |
|
|
| @property |
| def permeability(self): |
| """ |
| Returns magnetic permeability of the medium. |
| |
| Examples |
| ======== |
| |
| >>> from sympy.physics.optics import Medium |
| >>> m = Medium('m') |
| >>> m.permeability |
| pi*kilogram*meter/(2500000*ampere**2*second**2) |
| |
| """ |
| return self.args[2] |
|
|
| @property |
| def n(self): |
| return c*sqrt(self.permittivity*self.permeability) |
|
|