From 5045667eb555226f13f52281450c49694b361346 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E2=80=9CEmily?= <“emily.archer@desy.de”> Date: Tue, 8 Oct 2024 14:18:55 +0200 Subject: [PATCH 01/32] Added tests for LongitudinalProfileFromData Adding tests to allow for longitudinal profile from spectral data, whether monotonically increasing or decreasing --- tests/test_laser_profiles.py | 27 +++++++++++++++++++++++++++ 1 file changed, 27 insertions(+) diff --git a/tests/test_laser_profiles.py b/tests/test_laser_profiles.py index 354d0ee9..42643def 100644 --- a/tests/test_laser_profiles.py +++ b/tests/test_laser_profiles.py @@ -10,6 +10,7 @@ CosineLongitudinalProfile, GaussianLongitudinalProfile, SuperGaussianLongitudinalProfile, + LongitudinalProfileFromData, ) from lasy.profiles.profile import Profile, ScaledProfile, SummedProfile from lasy.profiles.transverse import ( @@ -233,6 +234,32 @@ def test_longitudinal_profiles(): print("cep_phase_th = ", cep_phase) print("cep_phase = ", cep_phase_cos) assert np.abs(cep_phase_cos - cep_phase) / cep_phase < 0.02 + + # LongitudinalProfileFromData + print("LongitudinalProfileFromData (monotonically increasing)") + tau = tau_fwhm / np.sqrt(2 * np.log(2)) + # Generate spectral data + profile_data = LongitudinalProfileFromData(data, np.min(t), np.max(t)) + field = profile_data.evaluate(t) + + + # The following are the actual tests + std_gauss = np.sqrt(np.average((t - t_peak) ** 2, weights=np.abs(field_gaussian))) + std_gauss_th = tau / np.sqrt(2.0) + print("std_th = ", std_gauss_th) + print("std = ", std_gauss) + assert np.abs(std_gauss - std_gauss_th) / std_gauss_th < 0.01 + + t_peak_gaussian = t[np.argmax(np.abs(field_gaussian))] + print("t_peak_th = ", t_peak) + print("t_peak = ", t_peak_gaussian) + assert np.abs(t_peak_gaussian - t_peak) / t_peak < 0.01 + + ff_gaussian = field_gaussian * np.exp(-1.0j * omega_0 * t) + cep_phase_gaussian = np.angle(ff_gaussian[np.argmax(np.abs(field_gaussian))]) + print("cep_phase_th = ", cep_phase) + print("cep_phase = ", cep_phase_gaussian) + assert np.abs(cep_phase_gaussian - cep_phase) / cep_phase < 0.02 def test_profile_gaussian_3d_cartesian(gaussian): From c325c05b8b51a05b3b1e59baa18c90c6ec4eeb38 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E2=80=9CEmily?= <“emily.archer@desy.de”> Date: Tue, 8 Oct 2024 14:22:44 +0200 Subject: [PATCH 02/32] Monotonically decreasing spectral data in LongitudinalProfileFromData Editing LongitudinalProfileFromData to allow for monotonically decreasing spectral data --- .../longitudinal_profile_from_data.py | 21 +++++++++++++++---- 1 file changed, 17 insertions(+), 4 deletions(-) diff --git a/lasy/profiles/longitudinal/longitudinal_profile_from_data.py b/lasy/profiles/longitudinal/longitudinal_profile_from_data.py index 7047f313..b817f4a3 100644 --- a/lasy/profiles/longitudinal/longitudinal_profile_from_data.py +++ b/lasy/profiles/longitudinal/longitudinal_profile_from_data.py @@ -29,7 +29,7 @@ class LongitudinalProfileFromData(LongitudinalProfile): axis : ndarrays of floats The horizontal axis of the pulse duration measurement. - The array must be monotonously increasing. + The array must be monotonically increasing or decreasing. When datatype is 'spectral' axis is wavelength in meters. When datatype is 'temporal' axis is time in seconds. @@ -64,12 +64,25 @@ def __init__(self, data, lo, hi): wavelength = data["axis"] assert np.all( np.diff(wavelength) > 0 - ), 'data["axis"] must be in monotonously increasing order.' - spectral_intensity = data["intensity"] + ) or np.all( + np.diff(wavelength) < 0 + ), 'data["axis"] must be in monotonically increasing or decreasing order.' + if np.all( + np.diff(wavelength) < 0 + ): + wavelength = wavelength[::-1] + spectral_intensity = data["intensity"][::-1] + else: + spectral_intensity = data["intensity"] if data.get("phase") is None: spectral_phase = np.zeros_like(wavelength) else: - spectral_phase = data["phase"] + if np.all( + np.diff(wavelength) < 0 + ): + spectral_phase = data["phase"][::-1] + else: + spectral_phase = data["phase"] dt = data["dt"] cwl = np.sum(spectral_intensity * wavelength) / np.sum(spectral_intensity) cfreq = c / cwl From 60a6fc6c058701a23d25b77f3c99fbe9b4617381 Mon Sep 17 00:00:00 2001 From: "pre-commit-ci[bot]" <66853113+pre-commit-ci[bot]@users.noreply.github.com> Date: Tue, 8 Oct 2024 12:43:48 +0000 Subject: [PATCH 03/32] [pre-commit.ci] auto fixes from pre-commit.com hooks for more information, see https://pre-commit.ci --- .../longitudinal/longitudinal_profile_from_data.py | 12 +++--------- tests/test_laser_profiles.py | 7 +++---- 2 files changed, 6 insertions(+), 13 deletions(-) diff --git a/lasy/profiles/longitudinal/longitudinal_profile_from_data.py b/lasy/profiles/longitudinal/longitudinal_profile_from_data.py index b817f4a3..6767c0ea 100644 --- a/lasy/profiles/longitudinal/longitudinal_profile_from_data.py +++ b/lasy/profiles/longitudinal/longitudinal_profile_from_data.py @@ -62,14 +62,10 @@ def __init__(self, data, lo, hi): if data["datatype"] == "spectral": # First find central frequency wavelength = data["axis"] - assert np.all( - np.diff(wavelength) > 0 - ) or np.all( + assert np.all(np.diff(wavelength) > 0) or np.all( np.diff(wavelength) < 0 ), 'data["axis"] must be in monotonically increasing or decreasing order.' - if np.all( - np.diff(wavelength) < 0 - ): + if np.all(np.diff(wavelength) < 0): wavelength = wavelength[::-1] spectral_intensity = data["intensity"][::-1] else: @@ -77,9 +73,7 @@ def __init__(self, data, lo, hi): if data.get("phase") is None: spectral_phase = np.zeros_like(wavelength) else: - if np.all( - np.diff(wavelength) < 0 - ): + if np.all(np.diff(wavelength) < 0): spectral_phase = data["phase"][::-1] else: spectral_phase = data["phase"] diff --git a/tests/test_laser_profiles.py b/tests/test_laser_profiles.py index 42643def..869879c1 100644 --- a/tests/test_laser_profiles.py +++ b/tests/test_laser_profiles.py @@ -9,8 +9,8 @@ from lasy.profiles.longitudinal import ( CosineLongitudinalProfile, GaussianLongitudinalProfile, - SuperGaussianLongitudinalProfile, LongitudinalProfileFromData, + SuperGaussianLongitudinalProfile, ) from lasy.profiles.profile import Profile, ScaledProfile, SummedProfile from lasy.profiles.transverse import ( @@ -234,15 +234,14 @@ def test_longitudinal_profiles(): print("cep_phase_th = ", cep_phase) print("cep_phase = ", cep_phase_cos) assert np.abs(cep_phase_cos - cep_phase) / cep_phase < 0.02 - + # LongitudinalProfileFromData print("LongitudinalProfileFromData (monotonically increasing)") tau = tau_fwhm / np.sqrt(2 * np.log(2)) # Generate spectral data profile_data = LongitudinalProfileFromData(data, np.min(t), np.max(t)) field = profile_data.evaluate(t) - - + # The following are the actual tests std_gauss = np.sqrt(np.average((t - t_peak) ** 2, weights=np.abs(field_gaussian))) std_gauss_th = tau / np.sqrt(2.0) From d67b2a2e27346aadc28706d02777aace9f68301f Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E2=80=9CEmily?= <“emily.archer@desy.de”> Date: Tue, 8 Oct 2024 15:43:47 +0200 Subject: [PATCH 04/32] Updated tests Updated tests for monotonically increasing or decreasing specta --- tests/test_laser_profiles.py | 54 ++++++++++++++++++++++++------------ 1 file changed, 37 insertions(+), 17 deletions(-) diff --git a/tests/test_laser_profiles.py b/tests/test_laser_profiles.py index 869879c1..c5c45701 100644 --- a/tests/test_laser_profiles.py +++ b/tests/test_laser_profiles.py @@ -11,6 +11,7 @@ GaussianLongitudinalProfile, LongitudinalProfileFromData, SuperGaussianLongitudinalProfile, + LongitudinalProfileFromData, ) from lasy.profiles.profile import Profile, ScaledProfile, SummedProfile from lasy.profiles.transverse import ( @@ -154,11 +155,14 @@ def test_longitudinal_profiles(): wavelength = 800e-9 tau_fwhm = 30.0e-15 + omega_fwhm = 4 * np.log(2) / tau_fwhm # Assumes fully-compressed t_peak = 1.0 * tau_fwhm cep_phase = 0.5 * np.pi omega_0 = 2.0 * np.pi * c / wavelength t = np.linspace(t_peak - 4 * tau_fwhm, t_peak + 4 * tau_fwhm, npoints) + omega = np.linspace(omega_0 - 4 * omega_fwhm, omega_0 + 4 * omega_fwhm, npoints) + wavelength = 2. * np.pi * c / omega # GaussianLongitudinalProfile print("GaussianLongitudinalProfile") @@ -235,31 +239,47 @@ def test_longitudinal_profiles(): print("cep_phase = ", cep_phase_cos) assert np.abs(cep_phase_cos - cep_phase) / cep_phase < 0.02 - # LongitudinalProfileFromData - print("LongitudinalProfileFromData (monotonically increasing)") - tau = tau_fwhm / np.sqrt(2 * np.log(2)) - # Generate spectral data + # LongitudinalProfileFromData - initially assuming zero phase + print("LongitudinalProfileFromData") + data = {} + data["datatype"] = "spectral" + Gamma = 2 * np.log(2) / tau_fwhm**2 # Generate spectral data assuming unchirped Gaussian + spectral_intensity = np.exp(-((omega - omega_0) ** 2) / (4.0 * Gamma)) + + print("Case 1: monotonically increasing spectral data") + data["axis"] = wavelength + data["intensity"] = spectral_intensity profile_data = LongitudinalProfileFromData(data, np.min(t), np.max(t)) - field = profile_data.evaluate(t) + field_data = profile_data.evaluate(t) - # The following are the actual tests - std_gauss = np.sqrt(np.average((t - t_peak) ** 2, weights=np.abs(field_gaussian))) + std_gauss_data = np.sqrt(np.average((t - t_peak) ** 2, weights=np.abs(field_data))) std_gauss_th = tau / np.sqrt(2.0) print("std_th = ", std_gauss_th) - print("std = ", std_gauss) - assert np.abs(std_gauss - std_gauss_th) / std_gauss_th < 0.01 + print("std = ", std_gauss_data) + assert np.abs(std_gauss_data - std_gauss_th) / std_gauss_th < 0.01 - t_peak_gaussian = t[np.argmax(np.abs(field_gaussian))] + t_peak_gaussian_data = t[np.argmax(np.abs(field_data))] print("t_peak_th = ", t_peak) - print("t_peak = ", t_peak_gaussian) - assert np.abs(t_peak_gaussian - t_peak) / t_peak < 0.01 + print("t_peak = ", t_peak_gaussian_data) + assert np.abs(t_peak_gaussian_data - t_peak) / t_peak < 0.01 + + print("Case 2: monotonically decreasing spectral data") + data["axis"] = wavelength[::-1] + data["intensity"] = spectral_intensity[::-1] + profile_data = LongitudinalProfileFromData(data, np.min(t), np.max(t)) + field_data = profile_data.evaluate(t) - ff_gaussian = field_gaussian * np.exp(-1.0j * omega_0 * t) - cep_phase_gaussian = np.angle(ff_gaussian[np.argmax(np.abs(field_gaussian))]) - print("cep_phase_th = ", cep_phase) - print("cep_phase = ", cep_phase_gaussian) - assert np.abs(cep_phase_gaussian - cep_phase) / cep_phase < 0.02 + std_gauss_data = np.sqrt(np.average((t - t_peak) ** 2, weights=np.abs(field_data))) + std_gauss_th = tau / np.sqrt(2.0) + print("std_th = ", std_gauss_th) + print("std = ", std_gauss_data) + assert np.abs(std_gauss_data - std_gauss_th) / std_gauss_th < 0.01 + t_peak_gaussian_data = t[np.argmax(np.abs(field_data))] + print("t_peak_th = ", t_peak) + print("t_peak = ", t_peak_gaussian_data) + assert np.abs(t_peak_gaussian_data - t_peak) / t_peak < 0.01 + def test_profile_gaussian_3d_cartesian(gaussian): # - 3D Cartesian case From 8dfae343833dc99bfabc10768d5c32b158d29b3d Mon Sep 17 00:00:00 2001 From: "pre-commit-ci[bot]" <66853113+pre-commit-ci[bot]@users.noreply.github.com> Date: Tue, 8 Oct 2024 13:45:04 +0000 Subject: [PATCH 05/32] [pre-commit.ci] auto fixes from pre-commit.com hooks for more information, see https://pre-commit.ci --- tests/test_laser_profiles.py | 15 ++++++++------- 1 file changed, 8 insertions(+), 7 deletions(-) diff --git a/tests/test_laser_profiles.py b/tests/test_laser_profiles.py index c5c45701..744b97ae 100644 --- a/tests/test_laser_profiles.py +++ b/tests/test_laser_profiles.py @@ -11,7 +11,6 @@ GaussianLongitudinalProfile, LongitudinalProfileFromData, SuperGaussianLongitudinalProfile, - LongitudinalProfileFromData, ) from lasy.profiles.profile import Profile, ScaledProfile, SummedProfile from lasy.profiles.transverse import ( @@ -155,14 +154,14 @@ def test_longitudinal_profiles(): wavelength = 800e-9 tau_fwhm = 30.0e-15 - omega_fwhm = 4 * np.log(2) / tau_fwhm # Assumes fully-compressed + omega_fwhm = 4 * np.log(2) / tau_fwhm # Assumes fully-compressed t_peak = 1.0 * tau_fwhm cep_phase = 0.5 * np.pi omega_0 = 2.0 * np.pi * c / wavelength t = np.linspace(t_peak - 4 * tau_fwhm, t_peak + 4 * tau_fwhm, npoints) omega = np.linspace(omega_0 - 4 * omega_fwhm, omega_0 + 4 * omega_fwhm, npoints) - wavelength = 2. * np.pi * c / omega + wavelength = 2.0 * np.pi * c / omega # GaussianLongitudinalProfile print("GaussianLongitudinalProfile") @@ -243,9 +242,11 @@ def test_longitudinal_profiles(): print("LongitudinalProfileFromData") data = {} data["datatype"] = "spectral" - Gamma = 2 * np.log(2) / tau_fwhm**2 # Generate spectral data assuming unchirped Gaussian + Gamma = ( + 2 * np.log(2) / tau_fwhm**2 + ) # Generate spectral data assuming unchirped Gaussian spectral_intensity = np.exp(-((omega - omega_0) ** 2) / (4.0 * Gamma)) - + print("Case 1: monotonically increasing spectral data") data["axis"] = wavelength data["intensity"] = spectral_intensity @@ -262,7 +263,7 @@ def test_longitudinal_profiles(): print("t_peak_th = ", t_peak) print("t_peak = ", t_peak_gaussian_data) assert np.abs(t_peak_gaussian_data - t_peak) / t_peak < 0.01 - + print("Case 2: monotonically decreasing spectral data") data["axis"] = wavelength[::-1] data["intensity"] = spectral_intensity[::-1] @@ -279,7 +280,7 @@ def test_longitudinal_profiles(): print("t_peak_th = ", t_peak) print("t_peak = ", t_peak_gaussian_data) assert np.abs(t_peak_gaussian_data - t_peak) / t_peak < 0.01 - + def test_profile_gaussian_3d_cartesian(gaussian): # - 3D Cartesian case From b38e4a462be113435c03b5ec53037efde111f6b4 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E2=80=9CEmily?= <“emily.archer@desy.de”> Date: Tue, 8 Oct 2024 15:49:16 +0200 Subject: [PATCH 06/32] Minor correction --- tests/test_laser_profiles.py | 1 + 1 file changed, 1 insertion(+) diff --git a/tests/test_laser_profiles.py b/tests/test_laser_profiles.py index c5c45701..5dd5453f 100644 --- a/tests/test_laser_profiles.py +++ b/tests/test_laser_profiles.py @@ -243,6 +243,7 @@ def test_longitudinal_profiles(): print("LongitudinalProfileFromData") data = {} data["datatype"] = "spectral" + data["dt"] = np.abs(t[1]-t[0]) Gamma = 2 * np.log(2) / tau_fwhm**2 # Generate spectral data assuming unchirped Gaussian spectral_intensity = np.exp(-((omega - omega_0) ** 2) / (4.0 * Gamma)) From 36f7e572ebf69fe65ff5b3a49203e87e40299f67 Mon Sep 17 00:00:00 2001 From: "pre-commit-ci[bot]" <66853113+pre-commit-ci[bot]@users.noreply.github.com> Date: Tue, 8 Oct 2024 13:57:29 +0000 Subject: [PATCH 07/32] [pre-commit.ci] auto fixes from pre-commit.com hooks for more information, see https://pre-commit.ci --- tests/test_laser_profiles.py | 15 ++++++++------- 1 file changed, 8 insertions(+), 7 deletions(-) diff --git a/tests/test_laser_profiles.py b/tests/test_laser_profiles.py index c5c45701..744b97ae 100644 --- a/tests/test_laser_profiles.py +++ b/tests/test_laser_profiles.py @@ -11,7 +11,6 @@ GaussianLongitudinalProfile, LongitudinalProfileFromData, SuperGaussianLongitudinalProfile, - LongitudinalProfileFromData, ) from lasy.profiles.profile import Profile, ScaledProfile, SummedProfile from lasy.profiles.transverse import ( @@ -155,14 +154,14 @@ def test_longitudinal_profiles(): wavelength = 800e-9 tau_fwhm = 30.0e-15 - omega_fwhm = 4 * np.log(2) / tau_fwhm # Assumes fully-compressed + omega_fwhm = 4 * np.log(2) / tau_fwhm # Assumes fully-compressed t_peak = 1.0 * tau_fwhm cep_phase = 0.5 * np.pi omega_0 = 2.0 * np.pi * c / wavelength t = np.linspace(t_peak - 4 * tau_fwhm, t_peak + 4 * tau_fwhm, npoints) omega = np.linspace(omega_0 - 4 * omega_fwhm, omega_0 + 4 * omega_fwhm, npoints) - wavelength = 2. * np.pi * c / omega + wavelength = 2.0 * np.pi * c / omega # GaussianLongitudinalProfile print("GaussianLongitudinalProfile") @@ -243,9 +242,11 @@ def test_longitudinal_profiles(): print("LongitudinalProfileFromData") data = {} data["datatype"] = "spectral" - Gamma = 2 * np.log(2) / tau_fwhm**2 # Generate spectral data assuming unchirped Gaussian + Gamma = ( + 2 * np.log(2) / tau_fwhm**2 + ) # Generate spectral data assuming unchirped Gaussian spectral_intensity = np.exp(-((omega - omega_0) ** 2) / (4.0 * Gamma)) - + print("Case 1: monotonically increasing spectral data") data["axis"] = wavelength data["intensity"] = spectral_intensity @@ -262,7 +263,7 @@ def test_longitudinal_profiles(): print("t_peak_th = ", t_peak) print("t_peak = ", t_peak_gaussian_data) assert np.abs(t_peak_gaussian_data - t_peak) / t_peak < 0.01 - + print("Case 2: monotonically decreasing spectral data") data["axis"] = wavelength[::-1] data["intensity"] = spectral_intensity[::-1] @@ -279,7 +280,7 @@ def test_longitudinal_profiles(): print("t_peak_th = ", t_peak) print("t_peak = ", t_peak_gaussian_data) assert np.abs(t_peak_gaussian_data - t_peak) / t_peak < 0.01 - + def test_profile_gaussian_3d_cartesian(gaussian): # - 3D Cartesian case From ff58c8b002c13c57ef6671f3170e2738f197de98 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E2=80=9CEmily?= <“emily.archer@desy.de”> Date: Tue, 8 Oct 2024 15:58:45 +0200 Subject: [PATCH 08/32] Minor correction --- tests/test_laser_profiles.py | 1 + 1 file changed, 1 insertion(+) diff --git a/tests/test_laser_profiles.py b/tests/test_laser_profiles.py index 744b97ae..764c64f7 100644 --- a/tests/test_laser_profiles.py +++ b/tests/test_laser_profiles.py @@ -242,6 +242,7 @@ def test_longitudinal_profiles(): print("LongitudinalProfileFromData") data = {} data["datatype"] = "spectral" + data["dt"] = np.abs(t[1]-t[0]) Gamma = ( 2 * np.log(2) / tau_fwhm**2 ) # Generate spectral data assuming unchirped Gaussian From c4dc18d266b9a3a88844e0aad4e917f2102f044f Mon Sep 17 00:00:00 2001 From: "pre-commit-ci[bot]" <66853113+pre-commit-ci[bot]@users.noreply.github.com> Date: Tue, 8 Oct 2024 13:59:06 +0000 Subject: [PATCH 09/32] [pre-commit.ci] auto fixes from pre-commit.com hooks for more information, see https://pre-commit.ci --- tests/test_laser_profiles.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/tests/test_laser_profiles.py b/tests/test_laser_profiles.py index 764c64f7..6e896222 100644 --- a/tests/test_laser_profiles.py +++ b/tests/test_laser_profiles.py @@ -242,7 +242,7 @@ def test_longitudinal_profiles(): print("LongitudinalProfileFromData") data = {} data["datatype"] = "spectral" - data["dt"] = np.abs(t[1]-t[0]) + data["dt"] = np.abs(t[1] - t[0]) Gamma = ( 2 * np.log(2) / tau_fwhm**2 ) # Generate spectral data assuming unchirped Gaussian From fd0dda11ca8a36411324ab37835db71965c6867b Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E2=80=9CEmily?= <“emily.archer@desy.de”> Date: Tue, 8 Oct 2024 16:12:50 +0200 Subject: [PATCH 10/32] Syntax --- tests/test_laser_profiles.py | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/tests/test_laser_profiles.py b/tests/test_laser_profiles.py index 6e896222..8a432acf 100644 --- a/tests/test_laser_profiles.py +++ b/tests/test_laser_profiles.py @@ -157,7 +157,7 @@ def test_longitudinal_profiles(): omega_fwhm = 4 * np.log(2) / tau_fwhm # Assumes fully-compressed t_peak = 1.0 * tau_fwhm cep_phase = 0.5 * np.pi - omega_0 = 2.0 * np.pi * c / wavelength + omega0 = 2.0 * np.pi * c / wavelength t = np.linspace(t_peak - 4 * tau_fwhm, t_peak + 4 * tau_fwhm, npoints) omega = np.linspace(omega_0 - 4 * omega_fwhm, omega_0 + 4 * omega_fwhm, npoints) @@ -246,7 +246,7 @@ def test_longitudinal_profiles(): Gamma = ( 2 * np.log(2) / tau_fwhm**2 ) # Generate spectral data assuming unchirped Gaussian - spectral_intensity = np.exp(-((omega - omega_0) ** 2) / (4.0 * Gamma)) + spectral_intensity = np.exp(-((omega - omega0) ** 2) / (4.0 * Gamma)) print("Case 1: monotonically increasing spectral data") data["axis"] = wavelength From 8667d7894ccdba3a78876ac656ec29bc992d9f3d Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E2=80=9CEmily?= <“emily.archer@desy.de”> Date: Wed, 9 Oct 2024 10:15:37 +0200 Subject: [PATCH 11/32] Syntax conflict Wavelength and wavelength axis given different names --- tests/test_laser_profiles.py | 16 +++++++--------- 1 file changed, 7 insertions(+), 9 deletions(-) diff --git a/tests/test_laser_profiles.py b/tests/test_laser_profiles.py index 8a432acf..251b1744 100644 --- a/tests/test_laser_profiles.py +++ b/tests/test_laser_profiles.py @@ -160,8 +160,8 @@ def test_longitudinal_profiles(): omega0 = 2.0 * np.pi * c / wavelength t = np.linspace(t_peak - 4 * tau_fwhm, t_peak + 4 * tau_fwhm, npoints) - omega = np.linspace(omega_0 - 4 * omega_fwhm, omega_0 + 4 * omega_fwhm, npoints) - wavelength = 2.0 * np.pi * c / omega + omega = np.linspace(omega0 - 4 * omega_fwhm, omega0 + 4 * omega_fwhm, npoints) + wavelength_axis = 2.0 * np.pi * c / omega # GaussianLongitudinalProfile print("GaussianLongitudinalProfile") @@ -242,14 +242,12 @@ def test_longitudinal_profiles(): print("LongitudinalProfileFromData") data = {} data["datatype"] = "spectral" - data["dt"] = np.abs(t[1] - t[0]) - Gamma = ( - 2 * np.log(2) / tau_fwhm**2 - ) # Generate spectral data assuming unchirped Gaussian - spectral_intensity = np.exp(-((omega - omega0) ** 2) / (4.0 * Gamma)) + data["dt"] = np.abs(t[1] - t[0]) # Generate spectral data assuming unchirped Gaussian + profile = np.exp(tau**2 * ((omega - omega0) ** 2) / 4.0 + + + 1.0j * (cep_phase + omega * t_peak)) print("Case 1: monotonically increasing spectral data") - data["axis"] = wavelength + data["axis"] = wavelength_axis data["intensity"] = spectral_intensity profile_data = LongitudinalProfileFromData(data, np.min(t), np.max(t)) field_data = profile_data.evaluate(t) @@ -266,7 +264,7 @@ def test_longitudinal_profiles(): assert np.abs(t_peak_gaussian_data - t_peak) / t_peak < 0.01 print("Case 2: monotonically decreasing spectral data") - data["axis"] = wavelength[::-1] + data["axis"] = wavelength_axis[::-1] data["intensity"] = spectral_intensity[::-1] profile_data = LongitudinalProfileFromData(data, np.min(t), np.max(t)) field_data = profile_data.evaluate(t) From aef6bef6bcfee9712827c3142527c55a76872d5a Mon Sep 17 00:00:00 2001 From: "pre-commit-ci[bot]" <66853113+pre-commit-ci[bot]@users.noreply.github.com> Date: Wed, 9 Oct 2024 08:18:08 +0000 Subject: [PATCH 12/32] [pre-commit.ci] auto fixes from pre-commit.com hooks for more information, see https://pre-commit.ci --- tests/test_laser_profiles.py | 9 ++++++--- 1 file changed, 6 insertions(+), 3 deletions(-) diff --git a/tests/test_laser_profiles.py b/tests/test_laser_profiles.py index 251b1744..2c942a15 100644 --- a/tests/test_laser_profiles.py +++ b/tests/test_laser_profiles.py @@ -242,9 +242,12 @@ def test_longitudinal_profiles(): print("LongitudinalProfileFromData") data = {} data["datatype"] = "spectral" - data["dt"] = np.abs(t[1] - t[0]) # Generate spectral data assuming unchirped Gaussian - profile = np.exp(tau**2 * ((omega - omega0) ** 2) / 4.0 + - + 1.0j * (cep_phase + omega * t_peak)) + data["dt"] = np.abs( + t[1] - t[0] + ) # Generate spectral data assuming unchirped Gaussian + profile = np.exp( + tau**2 * ((omega - omega0) ** 2) / 4.0 + +1.0j * (cep_phase + omega * t_peak) + ) print("Case 1: monotonically increasing spectral data") data["axis"] = wavelength_axis From 293fba0028f48a988c9992db2fdbfbe4d233f917 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E2=80=9CEmily?= <“emily.archer@desy.de”> Date: Wed, 9 Oct 2024 10:30:34 +0200 Subject: [PATCH 13/32] em-archer --- tests/test_laser_profiles.py | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/tests/test_laser_profiles.py b/tests/test_laser_profiles.py index 2c942a15..f45e71e7 100644 --- a/tests/test_laser_profiles.py +++ b/tests/test_laser_profiles.py @@ -157,10 +157,10 @@ def test_longitudinal_profiles(): omega_fwhm = 4 * np.log(2) / tau_fwhm # Assumes fully-compressed t_peak = 1.0 * tau_fwhm cep_phase = 0.5 * np.pi - omega0 = 2.0 * np.pi * c / wavelength + omega_0 = 2.0 * np.pi * c / wavelength t = np.linspace(t_peak - 4 * tau_fwhm, t_peak + 4 * tau_fwhm, npoints) - omega = np.linspace(omega0 - 4 * omega_fwhm, omega0 + 4 * omega_fwhm, npoints) + omega = np.linspace(omega_0 - 4 * omega_fwhm, omega_0 + 4 * omega_fwhm, npoints) wavelength_axis = 2.0 * np.pi * c / omega # GaussianLongitudinalProfile @@ -244,9 +244,9 @@ def test_longitudinal_profiles(): data["datatype"] = "spectral" data["dt"] = np.abs( t[1] - t[0] - ) # Generate spectral data assuming unchirped Gaussian + ) # Generate spectral data assuming sunchirped Gaussian profile = np.exp( - tau**2 * ((omega - omega0) ** 2) / 4.0 + +1.0j * (cep_phase + omega * t_peak) + tau**2 * ((omega - omega_0) ** 2) / 4.0 + +1.0j * (cep_phase + omega * t_peak) ) print("Case 1: monotonically increasing spectral data") From bb235176e8d2262d6f9d7340decff77bc0b1c76c Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E2=80=9CEmily?= <“emily.archer@desy.de”> Date: Wed, 9 Oct 2024 10:32:58 +0200 Subject: [PATCH 14/32] em-archer --- tests/test_laser_profiles.py | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/tests/test_laser_profiles.py b/tests/test_laser_profiles.py index f45e71e7..d400cf58 100644 --- a/tests/test_laser_profiles.py +++ b/tests/test_laser_profiles.py @@ -248,10 +248,13 @@ def test_longitudinal_profiles(): profile = np.exp( tau**2 * ((omega - omega_0) ** 2) / 4.0 + +1.0j * (cep_phase + omega * t_peak) ) + spectral_intensity = np.abs(profile) ** 2 / np.max(np.abs(profile) ** 2) + spectral_phase = np.unwrap(np.angle(profile)) print("Case 1: monotonically increasing spectral data") data["axis"] = wavelength_axis data["intensity"] = spectral_intensity + # data["phase"] = spectral_phase profile_data = LongitudinalProfileFromData(data, np.min(t), np.max(t)) field_data = profile_data.evaluate(t) @@ -269,6 +272,7 @@ def test_longitudinal_profiles(): print("Case 2: monotonically decreasing spectral data") data["axis"] = wavelength_axis[::-1] data["intensity"] = spectral_intensity[::-1] + # data["phase"] = spectral_phase[::-1] profile_data = LongitudinalProfileFromData(data, np.min(t), np.max(t)) field_data = profile_data.evaluate(t) From a366342b3e27232b2e973096bbee42c92ac9f359 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E2=80=9CEmily?= <“emily.archer@desy.de”> Date: Wed, 9 Oct 2024 10:37:41 +0200 Subject: [PATCH 15/32] Should now include phase Analytic ft of GaussianLongitudinalProfile needs checking --- tests/test_laser_profiles.py | 10 +++++----- 1 file changed, 5 insertions(+), 5 deletions(-) diff --git a/tests/test_laser_profiles.py b/tests/test_laser_profiles.py index d400cf58..b8233cbc 100644 --- a/tests/test_laser_profiles.py +++ b/tests/test_laser_profiles.py @@ -238,15 +238,15 @@ def test_longitudinal_profiles(): print("cep_phase = ", cep_phase_cos) assert np.abs(cep_phase_cos - cep_phase) / cep_phase < 0.02 - # LongitudinalProfileFromData - initially assuming zero phase + # LongitudinalProfileFromData print("LongitudinalProfileFromData") data = {} data["datatype"] = "spectral" data["dt"] = np.abs( t[1] - t[0] - ) # Generate spectral data assuming sunchirped Gaussian + ) # Generate spectral data assuming analytic ft of GaussianLongitudinalProfile profile = np.exp( - tau**2 * ((omega - omega_0) ** 2) / 4.0 + +1.0j * (cep_phase + omega * t_peak) + tau**2 * ((omega - omega_0) ** 2) / 4.0 + 1.0j * (cep_phase + omega * t_peak) ) spectral_intensity = np.abs(profile) ** 2 / np.max(np.abs(profile) ** 2) spectral_phase = np.unwrap(np.angle(profile)) @@ -254,7 +254,7 @@ def test_longitudinal_profiles(): print("Case 1: monotonically increasing spectral data") data["axis"] = wavelength_axis data["intensity"] = spectral_intensity - # data["phase"] = spectral_phase + data["phase"] = spectral_phase profile_data = LongitudinalProfileFromData(data, np.min(t), np.max(t)) field_data = profile_data.evaluate(t) @@ -272,7 +272,7 @@ def test_longitudinal_profiles(): print("Case 2: monotonically decreasing spectral data") data["axis"] = wavelength_axis[::-1] data["intensity"] = spectral_intensity[::-1] - # data["phase"] = spectral_phase[::-1] + data["phase"] = spectral_phase[::-1] profile_data = LongitudinalProfileFromData(data, np.min(t), np.max(t)) field_data = profile_data.evaluate(t) From bc0112b7ccbeae084494c55191cdd6adbc366c98 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E2=80=9CEmily?= <“emily.archer@desy.de”> Date: Wed, 9 Oct 2024 10:52:29 +0200 Subject: [PATCH 16/32] Final commit Analytic spectrum checked in separate script --- tests/test_laser_profiles.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/tests/test_laser_profiles.py b/tests/test_laser_profiles.py index b8233cbc..8a9cea40 100644 --- a/tests/test_laser_profiles.py +++ b/tests/test_laser_profiles.py @@ -246,7 +246,7 @@ def test_longitudinal_profiles(): t[1] - t[0] ) # Generate spectral data assuming analytic ft of GaussianLongitudinalProfile profile = np.exp( - tau**2 * ((omega - omega_0) ** 2) / 4.0 + 1.0j * (cep_phase + omega * t_peak) + - tau**2 * ((omega - omega_0) ** 2) / 4.0 + 1.0j * (cep_phase + omega * t_peak) ) spectral_intensity = np.abs(profile) ** 2 / np.max(np.abs(profile) ** 2) spectral_phase = np.unwrap(np.angle(profile)) From 695100812ba88989472fcbb836a58f24d5a73641 Mon Sep 17 00:00:00 2001 From: "pre-commit-ci[bot]" <66853113+pre-commit-ci[bot]@users.noreply.github.com> Date: Wed, 9 Oct 2024 08:52:40 +0000 Subject: [PATCH 17/32] [pre-commit.ci] auto fixes from pre-commit.com hooks for more information, see https://pre-commit.ci --- tests/test_laser_profiles.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/tests/test_laser_profiles.py b/tests/test_laser_profiles.py index 8a9cea40..dcd08289 100644 --- a/tests/test_laser_profiles.py +++ b/tests/test_laser_profiles.py @@ -246,7 +246,7 @@ def test_longitudinal_profiles(): t[1] - t[0] ) # Generate spectral data assuming analytic ft of GaussianLongitudinalProfile profile = np.exp( - - tau**2 * ((omega - omega_0) ** 2) / 4.0 + 1.0j * (cep_phase + omega * t_peak) + -(tau**2) * ((omega - omega_0) ** 2) / 4.0 + 1.0j * (cep_phase + omega * t_peak) ) spectral_intensity = np.abs(profile) ** 2 / np.max(np.abs(profile) ** 2) spectral_phase = np.unwrap(np.angle(profile)) From dfbb025b9480ee8b689a89beef70c9e1ebed7cc2 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E2=80=9CEmily?= <“emily.archer@desy.de”> Date: Wed, 9 Oct 2024 11:27:54 +0200 Subject: [PATCH 18/32] Fixing flipping of arrays --- .../longitudinal_profile_from_data.py | 15 ++++++--------- tests/test_laser_profiles.py | 6 ++---- 2 files changed, 8 insertions(+), 13 deletions(-) diff --git a/lasy/profiles/longitudinal/longitudinal_profile_from_data.py b/lasy/profiles/longitudinal/longitudinal_profile_from_data.py index 6767c0ea..5c015736 100644 --- a/lasy/profiles/longitudinal/longitudinal_profile_from_data.py +++ b/lasy/profiles/longitudinal/longitudinal_profile_from_data.py @@ -65,18 +65,15 @@ def __init__(self, data, lo, hi): assert np.all(np.diff(wavelength) > 0) or np.all( np.diff(wavelength) < 0 ), 'data["axis"] must be in monotonically increasing or decreasing order.' - if np.all(np.diff(wavelength) < 0): - wavelength = wavelength[::-1] - spectral_intensity = data["intensity"][::-1] - else: - spectral_intensity = data["intensity"] + spectral_intensity = data["intensity"] if data.get("phase") is None: spectral_phase = np.zeros_like(wavelength) else: - if np.all(np.diff(wavelength) < 0): - spectral_phase = data["phase"][::-1] - else: - spectral_phase = data["phase"] + spectral_phase = data["phase"] + if np.all(np.diff(wavelength) < 0: # Flip arrays + wavelength = wavelength[::-1] + spectral_intensity = spectral_intensity[::-1] + spectral_phase = spectral_phase[::-1] dt = data["dt"] cwl = np.sum(spectral_intensity * wavelength) / np.sum(spectral_intensity) cfreq = c / cwl diff --git a/tests/test_laser_profiles.py b/tests/test_laser_profiles.py index dcd08289..1e0b1d80 100644 --- a/tests/test_laser_profiles.py +++ b/tests/test_laser_profiles.py @@ -240,11 +240,9 @@ def test_longitudinal_profiles(): # LongitudinalProfileFromData print("LongitudinalProfileFromData") - data = {} + data = {} # Generate spectral data assuming analytic ft of GaussianLongitudinalProfile data["datatype"] = "spectral" - data["dt"] = np.abs( - t[1] - t[0] - ) # Generate spectral data assuming analytic ft of GaussianLongitudinalProfile + data["dt"] = 1e-15 profile = np.exp( -(tau**2) * ((omega - omega_0) ** 2) / 4.0 + 1.0j * (cep_phase + omega * t_peak) ) From 63854d34f85014af52fed34cdf099e54a1e66f5b Mon Sep 17 00:00:00 2001 From: "pre-commit-ci[bot]" <66853113+pre-commit-ci[bot]@users.noreply.github.com> Date: Wed, 9 Oct 2024 09:28:05 +0000 Subject: [PATCH 19/32] [pre-commit.ci] auto fixes from pre-commit.com hooks for more information, see https://pre-commit.ci --- tests/test_laser_profiles.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/tests/test_laser_profiles.py b/tests/test_laser_profiles.py index 1e0b1d80..381148db 100644 --- a/tests/test_laser_profiles.py +++ b/tests/test_laser_profiles.py @@ -240,7 +240,7 @@ def test_longitudinal_profiles(): # LongitudinalProfileFromData print("LongitudinalProfileFromData") - data = {} # Generate spectral data assuming analytic ft of GaussianLongitudinalProfile + data = {} # Generate spectral data assuming analytic ft of GaussianLongitudinalProfile data["datatype"] = "spectral" data["dt"] = 1e-15 profile = np.exp( From 7e231f16c85f3efdadd0edf2086b5f2ad728bd74 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E2=80=9CEmily?= <“emily.archer@desy.de”> Date: Wed, 9 Oct 2024 11:32:31 +0200 Subject: [PATCH 20/32] em-archer --- .../longitudinal_profile_from_data.py | 22 +++++++++++++------ 1 file changed, 15 insertions(+), 7 deletions(-) diff --git a/lasy/profiles/longitudinal/longitudinal_profile_from_data.py b/lasy/profiles/longitudinal/longitudinal_profile_from_data.py index 5c015736..ed611a05 100644 --- a/lasy/profiles/longitudinal/longitudinal_profile_from_data.py +++ b/lasy/profiles/longitudinal/longitudinal_profile_from_data.py @@ -62,18 +62,26 @@ def __init__(self, data, lo, hi): if data["datatype"] == "spectral": # First find central frequency wavelength = data["axis"] - assert np.all(np.diff(wavelength) > 0) or np.all( - np.diff(wavelength) < 0 - ), 'data["axis"] must be in monotonically increasing or decreasing order.' + assert np.all( + np.diff(wavelength) > 0 + ), 'data["axis"] must be in monotonously increasing order.' spectral_intensity = data["intensity"] if data.get("phase") is None: spectral_phase = np.zeros_like(wavelength) else: spectral_phase = data["phase"] - if np.all(np.diff(wavelength) < 0: # Flip arrays - wavelength = wavelength[::-1] - spectral_intensity = spectral_intensity[::-1] - spectral_phase = spectral_phase[::-1] + # assert np.all(np.diff(wavelength) > 0) or np.all( + # np.diff(wavelength) < 0 + # ), 'data["axis"] must be in monotonically increasing or decreasing order.' + # spectral_intensity = data["intensity"] + # if data.get("phase") is None: + # spectral_phase = np.zeros_like(wavelength) + # else: + # spectral_phase = data["phase"] + # if np.all(np.diff(wavelength) < 0: # Flip arrays + # wavelength = wavelength[::-1] + # spectral_intensity = spectral_intensity[::-1] + # spectral_phase = spectral_phase[::-1] dt = data["dt"] cwl = np.sum(spectral_intensity * wavelength) / np.sum(spectral_intensity) cfreq = c / cwl From e2ed1728c48eadcbb5542bbb83d71449d80b030f Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E2=80=9CEmily?= <“emily.archer@desy.de”> Date: Wed, 9 Oct 2024 11:51:23 +0200 Subject: [PATCH 21/32] Assertions also checked with separate notebook --- .../longitudinal_profile_from_data.py | 22 ++++++------------- 1 file changed, 7 insertions(+), 15 deletions(-) diff --git a/lasy/profiles/longitudinal/longitudinal_profile_from_data.py b/lasy/profiles/longitudinal/longitudinal_profile_from_data.py index ed611a05..e07e1481 100644 --- a/lasy/profiles/longitudinal/longitudinal_profile_from_data.py +++ b/lasy/profiles/longitudinal/longitudinal_profile_from_data.py @@ -62,26 +62,18 @@ def __init__(self, data, lo, hi): if data["datatype"] == "spectral": # First find central frequency wavelength = data["axis"] - assert np.all( - np.diff(wavelength) > 0 - ), 'data["axis"] must be in monotonously increasing order.' + assert np.all(np.diff(wavelength) > 0) or np.all( + np.diff(wavelength) < 0 + ), 'data["axis"] must be in monotonically increasing or decreasing order.' spectral_intensity = data["intensity"] if data.get("phase") is None: spectral_phase = np.zeros_like(wavelength) else: spectral_phase = data["phase"] - # assert np.all(np.diff(wavelength) > 0) or np.all( - # np.diff(wavelength) < 0 - # ), 'data["axis"] must be in monotonically increasing or decreasing order.' - # spectral_intensity = data["intensity"] - # if data.get("phase") is None: - # spectral_phase = np.zeros_like(wavelength) - # else: - # spectral_phase = data["phase"] - # if np.all(np.diff(wavelength) < 0: # Flip arrays - # wavelength = wavelength[::-1] - # spectral_intensity = spectral_intensity[::-1] - # spectral_phase = spectral_phase[::-1] + if np.all(np.diff(wavelength) < 0): # Flip arrays + wavelength = wavelength[::-1] + spectral_intensity = spectral_intensity[::-1] + spectral_phase = spectral_phase[::-1] dt = data["dt"] cwl = np.sum(spectral_intensity * wavelength) / np.sum(spectral_intensity) cfreq = c / cwl From d05893f9ec2931b2f2e7d02d583dd6dcf7c17049 Mon Sep 17 00:00:00 2001 From: "pre-commit-ci[bot]" <66853113+pre-commit-ci[bot]@users.noreply.github.com> Date: Wed, 9 Oct 2024 09:53:50 +0000 Subject: [PATCH 22/32] [pre-commit.ci] auto fixes from pre-commit.com hooks for more information, see https://pre-commit.ci --- lasy/profiles/longitudinal/longitudinal_profile_from_data.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/lasy/profiles/longitudinal/longitudinal_profile_from_data.py b/lasy/profiles/longitudinal/longitudinal_profile_from_data.py index e07e1481..31a291b0 100644 --- a/lasy/profiles/longitudinal/longitudinal_profile_from_data.py +++ b/lasy/profiles/longitudinal/longitudinal_profile_from_data.py @@ -70,7 +70,7 @@ def __init__(self, data, lo, hi): spectral_phase = np.zeros_like(wavelength) else: spectral_phase = data["phase"] - if np.all(np.diff(wavelength) < 0): # Flip arrays + if np.all(np.diff(wavelength) < 0): # Flip arrays wavelength = wavelength[::-1] spectral_intensity = spectral_intensity[::-1] spectral_phase = spectral_phase[::-1] From 5186fdd54b37f11ef4e7ae24e10730b64280f8e2 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E2=80=9CEmily?= <“emily.archer@desy.de”> Date: Wed, 9 Oct 2024 14:42:37 +0200 Subject: [PATCH 23/32] Increase time resolution --- tests/test_laser_profiles.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/tests/test_laser_profiles.py b/tests/test_laser_profiles.py index 381148db..1f8e873b 100644 --- a/tests/test_laser_profiles.py +++ b/tests/test_laser_profiles.py @@ -242,7 +242,7 @@ def test_longitudinal_profiles(): print("LongitudinalProfileFromData") data = {} # Generate spectral data assuming analytic ft of GaussianLongitudinalProfile data["datatype"] = "spectral" - data["dt"] = 1e-15 + data["dt"] = 1e-16 profile = np.exp( -(tau**2) * ((omega - omega_0) ** 2) / 4.0 + 1.0j * (cep_phase + omega * t_peak) ) From 4b2b40a219d5d23954275ecbd22622a3a83149d4 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E2=80=9CEmily?= <“emily.archer@desy.de”> Date: Thu, 10 Oct 2024 13:51:27 +0200 Subject: [PATCH 24/32] Modified to also allow spectral data to be specified with respect to omega When data["datatype"] = "spectral", data["axis"] can either be wavelength lambda in m or angular frequency omega in s^-1. The user doesn't need to specify, it will automatically detect and convert to wavelength if the latter is passed. --- .../longitudinal_profile_from_data.py | 16 +++++-- tests/test_laser_profiles.py | 42 +++++++++++++++++-- 2 files changed, 51 insertions(+), 7 deletions(-) diff --git a/lasy/profiles/longitudinal/longitudinal_profile_from_data.py b/lasy/profiles/longitudinal/longitudinal_profile_from_data.py index 31a291b0..804ae255 100644 --- a/lasy/profiles/longitudinal/longitudinal_profile_from_data.py +++ b/lasy/profiles/longitudinal/longitudinal_profile_from_data.py @@ -25,12 +25,15 @@ class LongitudinalProfileFromData(LongitudinalProfile): datatype : string The domain in which the data has been passed. Options - are 'spectral' and 'temporal' + are 'spectral' and 'temporal'. Spectral data may either be, + a) Wavelength dependent (lambda) or + b) Angular freuqency dependent (omega) axis : ndarrays of floats The horizontal axis of the pulse duration measurement. The array must be monotonically increasing or decreasing. - When datatype is 'spectral' axis is wavelength in meters. + When datatype is 'spectral' axis is wavelength in meters OR + angular frequency in 1/seconds. When datatype is 'temporal' axis is time in seconds. intensity : ndarrays of floats @@ -60,8 +63,13 @@ class LongitudinalProfileFromData(LongitudinalProfile): def __init__(self, data, lo, hi): if data["datatype"] == "spectral": - # First find central frequency - wavelength = data["axis"] + assert np.all(np.round(np.log10(data["axis"])) + 6.0 < 1.0) or np.all( + np.round(np.log10(data["axis"])) - 15.0 < 1.0 + ), 'data["axis"] must be wavelength [m] or angular frequency [s^-1].' + if np.all(np.round(np.log10(data["axis"])) + 6.0 < 1.0): + wavelength = data["axis"] # Accept as wavelength + else: + wavelength = 2.0 * np.pi * c / data["axis"] # Convert to wavelength assert np.all(np.diff(wavelength) > 0) or np.all( np.diff(wavelength) < 0 ), 'data["axis"] must be in monotonically increasing or decreasing order.' diff --git a/tests/test_laser_profiles.py b/tests/test_laser_profiles.py index 1f8e873b..4480889b 100644 --- a/tests/test_laser_profiles.py +++ b/tests/test_laser_profiles.py @@ -161,7 +161,7 @@ def test_longitudinal_profiles(): t = np.linspace(t_peak - 4 * tau_fwhm, t_peak + 4 * tau_fwhm, npoints) omega = np.linspace(omega_0 - 4 * omega_fwhm, omega_0 + 4 * omega_fwhm, npoints) - wavelength_axis = 2.0 * np.pi * c / omega + wavelength_axis = 2.0 * np.pi * c / omega # Note: monotonically decreasing # GaussianLongitudinalProfile print("GaussianLongitudinalProfile") @@ -249,7 +249,7 @@ def test_longitudinal_profiles(): spectral_intensity = np.abs(profile) ** 2 / np.max(np.abs(profile) ** 2) spectral_phase = np.unwrap(np.angle(profile)) - print("Case 1: monotonically increasing spectral data") + print("Case 1: monotonically decreasing data on wavelength axis") data["axis"] = wavelength_axis data["intensity"] = spectral_intensity data["phase"] = spectral_phase @@ -267,7 +267,7 @@ def test_longitudinal_profiles(): print("t_peak = ", t_peak_gaussian_data) assert np.abs(t_peak_gaussian_data - t_peak) / t_peak < 0.01 - print("Case 2: monotonically decreasing spectral data") + print("Case 2: monotonically increasing data on wavelength axis") data["axis"] = wavelength_axis[::-1] data["intensity"] = spectral_intensity[::-1] data["phase"] = spectral_phase[::-1] @@ -285,6 +285,42 @@ def test_longitudinal_profiles(): print("t_peak = ", t_peak_gaussian_data) assert np.abs(t_peak_gaussian_data - t_peak) / t_peak < 0.01 + print("Case 3: monotonically increasing data on angular frequency axis") + data["axis"] = omega + data["intensity"] = spectral_intensity + data["phase"] = spectral_phase + profile_data = LongitudinalProfileFromData(data, np.min(t), np.max(t)) + field_data = profile_data.evaluate(t) + + std_gauss_data = np.sqrt(np.average((t - t_peak) ** 2, weights=np.abs(field_data))) + std_gauss_th = tau / np.sqrt(2.0) + print("std_th = ", std_gauss_th) + print("std = ", std_gauss_data) + assert np.abs(std_gauss_data - std_gauss_th) / std_gauss_th < 0.01 + + t_peak_gaussian_data = t[np.argmax(np.abs(field_data))] + print("t_peak_th = ", t_peak) + print("t_peak = ", t_peak_gaussian_data) + assert np.abs(t_peak_gaussian_data - t_peak) / t_peak < 0.01 + + print("Case 4: monotonically decreasing data on angular frequency axis") + data["axis"] = omega[::-1] + data["intensity"] = spectral_intensity[::-1] + data["phase"] = spectral_phase[::-1] + profile_data = LongitudinalProfileFromData(data, np.min(t), np.max(t)) + field_data = profile_data.evaluate(t) + + std_gauss_data = np.sqrt(np.average((t - t_peak) ** 2, weights=np.abs(field_data))) + std_gauss_th = tau / np.sqrt(2.0) + print("std_th = ", std_gauss_th) + print("std = ", std_gauss_data) + assert np.abs(std_gauss_data - std_gauss_th) / std_gauss_th < 0.01 + + t_peak_gaussian_data = t[np.argmax(np.abs(field_data))] + print("t_peak_th = ", t_peak) + print("t_peak = ", t_peak_gaussian_data) + assert np.abs(t_peak_gaussian_data - t_peak) / t_peak < 0.01 + def test_profile_gaussian_3d_cartesian(gaussian): # - 3D Cartesian case From 804f5bf3052f9c89ca80a7c619b138dfe2c4acfd Mon Sep 17 00:00:00 2001 From: "pre-commit-ci[bot]" <66853113+pre-commit-ci[bot]@users.noreply.github.com> Date: Thu, 10 Oct 2024 11:51:56 +0000 Subject: [PATCH 25/32] [pre-commit.ci] auto fixes from pre-commit.com hooks for more information, see https://pre-commit.ci --- lasy/profiles/longitudinal/longitudinal_profile_from_data.py | 4 ++-- tests/test_laser_profiles.py | 4 ++-- 2 files changed, 4 insertions(+), 4 deletions(-) diff --git a/lasy/profiles/longitudinal/longitudinal_profile_from_data.py b/lasy/profiles/longitudinal/longitudinal_profile_from_data.py index 804ae255..dcc3892f 100644 --- a/lasy/profiles/longitudinal/longitudinal_profile_from_data.py +++ b/lasy/profiles/longitudinal/longitudinal_profile_from_data.py @@ -67,9 +67,9 @@ def __init__(self, data, lo, hi): np.round(np.log10(data["axis"])) - 15.0 < 1.0 ), 'data["axis"] must be wavelength [m] or angular frequency [s^-1].' if np.all(np.round(np.log10(data["axis"])) + 6.0 < 1.0): - wavelength = data["axis"] # Accept as wavelength + wavelength = data["axis"] # Accept as wavelength else: - wavelength = 2.0 * np.pi * c / data["axis"] # Convert to wavelength + wavelength = 2.0 * np.pi * c / data["axis"] # Convert to wavelength assert np.all(np.diff(wavelength) > 0) or np.all( np.diff(wavelength) < 0 ), 'data["axis"] must be in monotonically increasing or decreasing order.' diff --git a/tests/test_laser_profiles.py b/tests/test_laser_profiles.py index 4480889b..486ef3c9 100644 --- a/tests/test_laser_profiles.py +++ b/tests/test_laser_profiles.py @@ -161,7 +161,7 @@ def test_longitudinal_profiles(): t = np.linspace(t_peak - 4 * tau_fwhm, t_peak + 4 * tau_fwhm, npoints) omega = np.linspace(omega_0 - 4 * omega_fwhm, omega_0 + 4 * omega_fwhm, npoints) - wavelength_axis = 2.0 * np.pi * c / omega # Note: monotonically decreasing + wavelength_axis = 2.0 * np.pi * c / omega # Note: monotonically decreasing # GaussianLongitudinalProfile print("GaussianLongitudinalProfile") @@ -302,7 +302,7 @@ def test_longitudinal_profiles(): print("t_peak_th = ", t_peak) print("t_peak = ", t_peak_gaussian_data) assert np.abs(t_peak_gaussian_data - t_peak) / t_peak < 0.01 - + print("Case 4: monotonically decreasing data on angular frequency axis") data["axis"] = omega[::-1] data["intensity"] = spectral_intensity[::-1] From fb5aabc9f798df6cc657e3d6767c44e46b80fc27 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E2=80=9CEmily?= <“emily.archer@desy.de”> Date: Mon, 14 Oct 2024 13:19:00 +0200 Subject: [PATCH 26/32] Added requirement for user to specify axis type User must now specify axis type (wavelength by default). Also added proper conversion for spectral intensity if axis is omega. --- .../longitudinal/longitudinal_profile_from_data.py | 14 +++++++------- tests/test_laser_profiles.py | 4 +++- 2 files changed, 10 insertions(+), 8 deletions(-) diff --git a/lasy/profiles/longitudinal/longitudinal_profile_from_data.py b/lasy/profiles/longitudinal/longitudinal_profile_from_data.py index dcc3892f..9cb5615f 100644 --- a/lasy/profiles/longitudinal/longitudinal_profile_from_data.py +++ b/lasy/profiles/longitudinal/longitudinal_profile_from_data.py @@ -26,8 +26,8 @@ class LongitudinalProfileFromData(LongitudinalProfile): datatype : string The domain in which the data has been passed. Options are 'spectral' and 'temporal'. Spectral data may either be, - a) Wavelength dependent (lambda) or - b) Angular freuqency dependent (omega) + a) Wavelength dependent (lambda): data["axis_is_wavelength"] = True or + b) Angular freuqency dependent (omega): data["axis_is_wavelength"] = False axis : ndarrays of floats The horizontal axis of the pulse duration measurement. @@ -63,17 +63,17 @@ class LongitudinalProfileFromData(LongitudinalProfile): def __init__(self, data, lo, hi): if data["datatype"] == "spectral": - assert np.all(np.round(np.log10(data["axis"])) + 6.0 < 1.0) or np.all( - np.round(np.log10(data["axis"])) - 15.0 < 1.0 - ), 'data["axis"] must be wavelength [m] or angular frequency [s^-1].' - if np.all(np.round(np.log10(data["axis"])) + 6.0 < 1.0): + if not "axis_is_wavelength" in data: # Set to wavelength data by default + data["axis_is_wavelength"] = True + if data["axis_is_wavelength"]: wavelength = data["axis"] # Accept as wavelength + spectral_intensity = data["intensity"] else: wavelength = 2.0 * np.pi * c / data["axis"] # Convert to wavelength + spectral_intensity = data["intensity"] * 2.0 * np.pi * c / wavelength ** 2 # Convert spectral data assert np.all(np.diff(wavelength) > 0) or np.all( np.diff(wavelength) < 0 ), 'data["axis"] must be in monotonically increasing or decreasing order.' - spectral_intensity = data["intensity"] if data.get("phase") is None: spectral_phase = np.zeros_like(wavelength) else: diff --git a/tests/test_laser_profiles.py b/tests/test_laser_profiles.py index 486ef3c9..5bdf6f81 100644 --- a/tests/test_laser_profiles.py +++ b/tests/test_laser_profiles.py @@ -240,7 +240,7 @@ def test_longitudinal_profiles(): # LongitudinalProfileFromData print("LongitudinalProfileFromData") - data = {} # Generate spectral data assuming analytic ft of GaussianLongitudinalProfile + data = {} # Generate spectral data assuming analytic Fourier transform of GaussianLongitudinalProfile data["datatype"] = "spectral" data["dt"] = 1e-16 profile = np.exp( @@ -289,6 +289,7 @@ def test_longitudinal_profiles(): data["axis"] = omega data["intensity"] = spectral_intensity data["phase"] = spectral_phase + data["axis_is_wavelength"] = False profile_data = LongitudinalProfileFromData(data, np.min(t), np.max(t)) field_data = profile_data.evaluate(t) @@ -307,6 +308,7 @@ def test_longitudinal_profiles(): data["axis"] = omega[::-1] data["intensity"] = spectral_intensity[::-1] data["phase"] = spectral_phase[::-1] + data["axis_is_wavelength"] = False profile_data = LongitudinalProfileFromData(data, np.min(t), np.max(t)) field_data = profile_data.evaluate(t) From 07ada48ead14831f2f177ffd7ae7b643bfd021ff Mon Sep 17 00:00:00 2001 From: "pre-commit-ci[bot]" <66853113+pre-commit-ci[bot]@users.noreply.github.com> Date: Mon, 14 Oct 2024 11:28:38 +0000 Subject: [PATCH 27/32] [pre-commit.ci] auto fixes from pre-commit.com hooks for more information, see https://pre-commit.ci --- .../profiles/longitudinal/longitudinal_profile_from_data.py | 6 ++++-- 1 file changed, 4 insertions(+), 2 deletions(-) diff --git a/lasy/profiles/longitudinal/longitudinal_profile_from_data.py b/lasy/profiles/longitudinal/longitudinal_profile_from_data.py index 9cb5615f..08ff6ad5 100644 --- a/lasy/profiles/longitudinal/longitudinal_profile_from_data.py +++ b/lasy/profiles/longitudinal/longitudinal_profile_from_data.py @@ -63,14 +63,16 @@ class LongitudinalProfileFromData(LongitudinalProfile): def __init__(self, data, lo, hi): if data["datatype"] == "spectral": - if not "axis_is_wavelength" in data: # Set to wavelength data by default + if "axis_is_wavelength" not in data: # Set to wavelength data by default data["axis_is_wavelength"] = True if data["axis_is_wavelength"]: wavelength = data["axis"] # Accept as wavelength spectral_intensity = data["intensity"] else: wavelength = 2.0 * np.pi * c / data["axis"] # Convert to wavelength - spectral_intensity = data["intensity"] * 2.0 * np.pi * c / wavelength ** 2 # Convert spectral data + spectral_intensity = ( + data["intensity"] * 2.0 * np.pi * c / wavelength**2 + ) # Convert spectral data assert np.all(np.diff(wavelength) > 0) or np.all( np.diff(wavelength) < 0 ), 'data["axis"] must be in monotonically increasing or decreasing order.' From e6dab5da94107aa1013d22c2244fde08fa22859a Mon Sep 17 00:00:00 2001 From: Emily Archer Date: Wed, 16 Oct 2024 15:48:47 +0200 Subject: [PATCH 28/32] Update lasy/profiles/longitudinal/longitudinal_profile_from_data.py MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Co-authored-by: Maxence Thévenet --- lasy/profiles/longitudinal/longitudinal_profile_from_data.py | 4 +--- 1 file changed, 1 insertion(+), 3 deletions(-) diff --git a/lasy/profiles/longitudinal/longitudinal_profile_from_data.py b/lasy/profiles/longitudinal/longitudinal_profile_from_data.py index 08ff6ad5..40380ead 100644 --- a/lasy/profiles/longitudinal/longitudinal_profile_from_data.py +++ b/lasy/profiles/longitudinal/longitudinal_profile_from_data.py @@ -25,9 +25,7 @@ class LongitudinalProfileFromData(LongitudinalProfile): datatype : string The domain in which the data has been passed. Options - are 'spectral' and 'temporal'. Spectral data may either be, - a) Wavelength dependent (lambda): data["axis_is_wavelength"] = True or - b) Angular freuqency dependent (omega): data["axis_is_wavelength"] = False + are 'spectral' and 'temporal'. axis : ndarrays of floats The horizontal axis of the pulse duration measurement. From 1c6f7a33500099475e3c85428c84df5ba6a84636 Mon Sep 17 00:00:00 2001 From: Emily Archer Date: Wed, 16 Oct 2024 15:48:56 +0200 Subject: [PATCH 29/32] Update lasy/profiles/longitudinal/longitudinal_profile_from_data.py MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Co-authored-by: Maxence Thévenet --- lasy/profiles/longitudinal/longitudinal_profile_from_data.py | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/lasy/profiles/longitudinal/longitudinal_profile_from_data.py b/lasy/profiles/longitudinal/longitudinal_profile_from_data.py index 40380ead..7ccb5e61 100644 --- a/lasy/profiles/longitudinal/longitudinal_profile_from_data.py +++ b/lasy/profiles/longitudinal/longitudinal_profile_from_data.py @@ -27,6 +27,10 @@ class LongitudinalProfileFromData(LongitudinalProfile): The domain in which the data has been passed. Options are 'spectral' and 'temporal'. + axis_is_wavelength : boolean (optional, default True) + If True, the axis represents wavelength in [m] (SI). + If False, it represents frequency in [1/s] (SI). + axis : ndarrays of floats The horizontal axis of the pulse duration measurement. The array must be monotonically increasing or decreasing. From 245bfaf76b4da60c82b3229a2b62f9aa0d4000e0 Mon Sep 17 00:00:00 2001 From: Maxence Thevenet Date: Thu, 17 Oct 2024 21:08:04 +1000 Subject: [PATCH 30/32] avoid modifying input variable --- .../longitudinal/longitudinal_profile_from_data.py | 7 ++++--- 1 file changed, 4 insertions(+), 3 deletions(-) diff --git a/lasy/profiles/longitudinal/longitudinal_profile_from_data.py b/lasy/profiles/longitudinal/longitudinal_profile_from_data.py index 7ccb5e61..67ab5edc 100644 --- a/lasy/profiles/longitudinal/longitudinal_profile_from_data.py +++ b/lasy/profiles/longitudinal/longitudinal_profile_from_data.py @@ -65,9 +65,10 @@ class LongitudinalProfileFromData(LongitudinalProfile): def __init__(self, data, lo, hi): if data["datatype"] == "spectral": - if "axis_is_wavelength" not in data: # Set to wavelength data by default - data["axis_is_wavelength"] = True - if data["axis_is_wavelength"]: + axis_is_wavelength = True # Set to wavelength data by default + if "axis_is_wavelength" in data: + axis_is_wavelength = data["axis_is_wavelength"] + if axis_is_wavelength: wavelength = data["axis"] # Accept as wavelength spectral_intensity = data["intensity"] else: From 2635e65e578c0ed92cd71ff5a02290c912be9e1f Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Maxence=20Th=C3=A9venet?= Date: Thu, 17 Oct 2024 21:09:54 +1000 Subject: [PATCH 31/32] Update lasy/profiles/longitudinal/longitudinal_profile_from_data.py --- lasy/profiles/longitudinal/longitudinal_profile_from_data.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/lasy/profiles/longitudinal/longitudinal_profile_from_data.py b/lasy/profiles/longitudinal/longitudinal_profile_from_data.py index 67ab5edc..81fdb68d 100644 --- a/lasy/profiles/longitudinal/longitudinal_profile_from_data.py +++ b/lasy/profiles/longitudinal/longitudinal_profile_from_data.py @@ -35,7 +35,7 @@ class LongitudinalProfileFromData(LongitudinalProfile): The horizontal axis of the pulse duration measurement. The array must be monotonically increasing or decreasing. When datatype is 'spectral' axis is wavelength in meters OR - angular frequency in 1/seconds. + frequency in 1/seconds. When datatype is 'temporal' axis is time in seconds. intensity : ndarrays of floats From be30ab82662f349606fab8e7e9e2e3f37859dbf9 Mon Sep 17 00:00:00 2001 From: Maxence Thevenet Date: Thu, 17 Oct 2024 21:18:06 +1000 Subject: [PATCH 32/32] typo --- lasy/profiles/longitudinal/longitudinal_profile_from_data.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/lasy/profiles/longitudinal/longitudinal_profile_from_data.py b/lasy/profiles/longitudinal/longitudinal_profile_from_data.py index 81fdb68d..d987ee69 100644 --- a/lasy/profiles/longitudinal/longitudinal_profile_from_data.py +++ b/lasy/profiles/longitudinal/longitudinal_profile_from_data.py @@ -35,7 +35,7 @@ class LongitudinalProfileFromData(LongitudinalProfile): The horizontal axis of the pulse duration measurement. The array must be monotonically increasing or decreasing. When datatype is 'spectral' axis is wavelength in meters OR - frequency in 1/seconds. + frequency in 1/seconds. When datatype is 'temporal' axis is time in seconds. intensity : ndarrays of floats