From 74bb9a9bc27ad10055ad301de43ab92c7d2b2feb Mon Sep 17 00:00:00 2001 From: perceptualrobots Date: Thu, 3 Aug 2023 19:55:50 +0100 Subject: [PATCH 1/6] b4 adding wind speed --- nbs/12_yaw_module.ipynb | 7 +++++++ 1 file changed, 7 insertions(+) diff --git a/nbs/12_yaw_module.ipynb b/nbs/12_yaw_module.ipynb index 2a436f21..d933cfbd 100644 --- a/nbs/12_yaw_module.ipynb +++ b/nbs/12_yaw_module.ipynb @@ -312,6 +312,9 @@ " ]\n", " )\n", "\n", + " # added wind speed\n", + " print(self.wind_timeseries[\"wind_speed\"][self.index_wind_timeseries])\n", + "\n", " self.state = new_state\n", " reward = -self.wind_timeseries[\"wind_speed\"][self.index_wind_timeseries]**3 * oriented_angle(self.yaw_angle - self.wind_timeseries[\"wind_direction\"][self.index_wind_timeseries:self.index_wind_timeseries+12].mean()) ** 2 \\\n", " + self.w2 * (self.step_since_last_2 > self.filter_duration and self.step_since_last_0 > self.filter_duration)\n", @@ -558,6 +561,10 @@ "display_name": "python3", "language": "python", "name": "python3" + }, + "language_info": { + "name": "python", + "version": "3.9.11" } }, "nbformat": 4, From b17b515cb441bbca79bf966b2885ad35806cb722 Mon Sep 17 00:00:00 2001 From: perceptualrobots Date: Thu, 3 Aug 2023 19:58:56 +0100 Subject: [PATCH 2/6] update --- nbs/12_yaw_module.ipynb | 6 ++++-- 1 file changed, 4 insertions(+), 2 deletions(-) diff --git a/nbs/12_yaw_module.ipynb b/nbs/12_yaw_module.ipynb index d933cfbd..e5e2178b 100644 --- a/nbs/12_yaw_module.ipynb +++ b/nbs/12_yaw_module.ipynb @@ -301,14 +301,16 @@ "\n", " self.yaw_angle = oriented_angle(self.yaw_angle + yaw_angle_change)\n", " new_yaw_error = oriented_angle(self.yaw_angle - self.wind_timeseries[\"wind_direction\"][self.index_wind_timeseries])\n", - " new_state = np.zeros((self.ancestors, 4))\n", + " new_state = np.zeros((self.ancestors, 5))\n", " new_state[:-1, :] = self.state[1:, :]\n", " new_state[-1, :] = np.array(\n", " [\n", " action,\n", " new_yaw_error,\n", " self.wind_timeseries[\"wind_direction\"][self.index_wind_timeseries],\n", - " (self.wind_timeseries[\"wind_speed\"][self.index_wind_timeseries]-self.wind_speed_avg)/self.wind_speed_std,\n", + " (self.wind_timeseries[\"wind_speed\"][self.index_wind_timeseries]-self.wind_speed_avg)/self.wind_speed_std, \n", + " self.wind_timeseries[\"wind_speed\"][self.index_wind_timeseries]\n", + "\n", " ]\n", " )\n", "\n", From 405e9856054b24637a7a47ffeadbe332190a61bb Mon Sep 17 00:00:00 2001 From: perceptualrobots Date: Thu, 3 Aug 2023 20:58:43 +0100 Subject: [PATCH 3/6] update --- nbs/05_environments.ipynb | 7 ++++--- nbs/12_yaw_module.ipynb | 16 +++++----------- pct/environments.py | 7 ++++--- pct/yaw_module.py | 8 ++++++-- 4 files changed, 19 insertions(+), 19 deletions(-) diff --git a/nbs/05_environments.ipynb b/nbs/05_environments.ipynb index f5749a7f..5347e02d 100644 --- a/nbs/05_environments.ipynb +++ b/nbs/05_environments.ipynb @@ -691,11 +691,12 @@ "\n", " def parse_obs(self):\n", " self.value = self.obs[0][-1]\n", - " self.reward = self.obs[1]\n", - " self.done = self.obs[2]\n", - " self.info = self.obs[3]\n", + " self.reward = self.obs[2]\n", + " self.done = self.obs[3]\n", + " self.info = self.obs[4]\n", "\n", " def process_values(self):\n", + " self.value = np.append(self.value, self.obs[1])\n", " pass\n", " # raise Exception(f'TBD {self.__class__.__name__}:{self.env_name}.')\n", "\n", diff --git a/nbs/12_yaw_module.ipynb b/nbs/12_yaw_module.ipynb index e5e2178b..762ea783 100644 --- a/nbs/12_yaw_module.ipynb +++ b/nbs/12_yaw_module.ipynb @@ -237,12 +237,12 @@ "\n", " wind_timeseries,start_index,stop_index,ancestors,filter_duration,params,keep_history = get_properties(properties)\n", " \n", - "\n", " self.wind_timeseries = wind_timeseries\n", " self.start_index = start_index\n", " self.stop_index = stop_index\n", " self.wind_speed_avg = wind_timeseries['wind_speed'][start_index:stop_index].mean()\n", " self.wind_speed_std = wind_timeseries['wind_speed'][start_index:stop_index].std()\n", + " # mean=6.688939999999999 std=1.0833884838814778\n", " self.keep_history = keep_history\n", " self.filter_duration = filter_duration\n", " self.yaw_rate_max = params[\"yaw_rate_max\"]\n", @@ -301,21 +301,19 @@ "\n", " self.yaw_angle = oriented_angle(self.yaw_angle + yaw_angle_change)\n", " new_yaw_error = oriented_angle(self.yaw_angle - self.wind_timeseries[\"wind_direction\"][self.index_wind_timeseries])\n", - " new_state = np.zeros((self.ancestors, 5))\n", + " new_state = np.zeros((self.ancestors, 4))\n", " new_state[:-1, :] = self.state[1:, :]\n", " new_state[-1, :] = np.array(\n", " [\n", " action,\n", " new_yaw_error,\n", " self.wind_timeseries[\"wind_direction\"][self.index_wind_timeseries],\n", - " (self.wind_timeseries[\"wind_speed\"][self.index_wind_timeseries]-self.wind_speed_avg)/self.wind_speed_std, \n", - " self.wind_timeseries[\"wind_speed\"][self.index_wind_timeseries]\n", - "\n", + " (self.wind_timeseries[\"wind_speed\"][self.index_wind_timeseries]-self.wind_speed_avg)/self.wind_speed_std\n", " ]\n", " )\n", "\n", " # added wind speed\n", - " print(self.wind_timeseries[\"wind_speed\"][self.index_wind_timeseries])\n", + " wind_speed = self.wind_timeseries[\"wind_speed\"][self.index_wind_timeseries]\n", "\n", " self.state = new_state\n", " reward = -self.wind_timeseries[\"wind_speed\"][self.index_wind_timeseries]**3 * oriented_angle(self.yaw_angle - self.wind_timeseries[\"wind_direction\"][self.index_wind_timeseries:self.index_wind_timeseries+12].mean()) ** 2 \\\n", @@ -374,7 +372,7 @@ " if self.index_wind_timeseries == self.stop_index - 1:\n", " done = True\n", "\n", - " return self.state, reward, done, {}\n", + " return self.state, wind_speed, reward, done, {}\n", " \n", " \n", "\n", @@ -563,10 +561,6 @@ "display_name": "python3", "language": "python", "name": "python3" - }, - "language_info": { - "name": "python", - "version": "3.9.11" } }, "nbformat": 4, diff --git a/pct/environments.py b/pct/environments.py index ad3e4c73..37a2039e 100644 --- a/pct/environments.py +++ b/pct/environments.py @@ -545,11 +545,12 @@ def apply_actions_get_obs(self): def parse_obs(self): self.value = self.obs[0][-1] - self.reward = self.obs[1] - self.done = self.obs[2] - self.info = self.obs[3] + self.reward = self.obs[2] + self.done = self.obs[3] + self.info = self.obs[4] def process_values(self): + self.value = np.append(self.value, self.obs[1]) pass # raise Exception(f'TBD {self.__class__.__name__}:{self.env_name}.') diff --git a/pct/yaw_module.py b/pct/yaw_module.py index c89d011f..f87ace12 100644 --- a/pct/yaw_module.py +++ b/pct/yaw_module.py @@ -171,6 +171,7 @@ def initialise(self, properties ): self.stop_index = stop_index self.wind_speed_avg = wind_timeseries['wind_speed'][start_index:stop_index].mean() self.wind_speed_std = wind_timeseries['wind_speed'][start_index:stop_index].std() + # mean=6.688939999999999 std=1.0833884838814778 self.keep_history = keep_history self.filter_duration = filter_duration self.yaw_rate_max = params["yaw_rate_max"] @@ -236,10 +237,13 @@ def step(self, action): action, new_yaw_error, self.wind_timeseries["wind_direction"][self.index_wind_timeseries], - (self.wind_timeseries["wind_speed"][self.index_wind_timeseries]-self.wind_speed_avg)/self.wind_speed_std, + (self.wind_timeseries["wind_speed"][self.index_wind_timeseries]-self.wind_speed_avg)/self.wind_speed_std ] ) + # added wind speed + wind_speed = self.wind_timeseries["wind_speed"][self.index_wind_timeseries] + self.state = new_state reward = -self.wind_timeseries["wind_speed"][self.index_wind_timeseries]**3 * oriented_angle(self.yaw_angle - self.wind_timeseries["wind_direction"][self.index_wind_timeseries:self.index_wind_timeseries+12].mean()) ** 2 \ + self.w2 * (self.step_since_last_2 > self.filter_duration and self.step_since_last_0 > self.filter_duration) @@ -297,7 +301,7 @@ def step(self, action): if self.index_wind_timeseries == self.stop_index - 1: done = True - return self.state, reward, done, {} + return self.state, wind_speed, reward, done, {} From 314cc5777041bfa7522d8c7ca852337990586f5c Mon Sep 17 00:00:00 2001 From: perceptualrobots Date: Fri, 4 Aug 2023 22:16:23 +0100 Subject: [PATCH 4/6] update --- pct/yaw_module.py | 1 - 1 file changed, 1 deletion(-) diff --git a/pct/yaw_module.py b/pct/yaw_module.py index f87ace12..e06bd216 100644 --- a/pct/yaw_module.py +++ b/pct/yaw_module.py @@ -165,7 +165,6 @@ def initialise(self, properties ): wind_timeseries,start_index,stop_index,ancestors,filter_duration,params,keep_history = get_properties(properties) - self.wind_timeseries = wind_timeseries self.start_index = start_index self.stop_index = stop_index From ccd479e509e7e161de56df69ef5cae539e0fa9a8 Mon Sep 17 00:00:00 2001 From: perceptualrobots Date: Sat, 5 Aug 2023 17:47:18 +0100 Subject: [PATCH 5/6] update --- nbs/05_environments.ipynb | 18 ++++++++++------- nbs/07_errors.ipynb | 25 +++++++++++++++++++++++ nbs/12_yaw_module.ipynb | 2 +- pct/_modidx.py | 5 +++++ pct/environments.py | 18 ++++++++++------- pct/errors.py | 42 ++++++++++++++++++++++++++++----------- pct/yaw_module.py | 2 +- 7 files changed, 84 insertions(+), 28 deletions(-) diff --git a/nbs/05_environments.ipynb b/nbs/05_environments.ipynb index 5347e02d..8856d5e9 100644 --- a/nbs/05_environments.ipynb +++ b/nbs/05_environments.ipynb @@ -654,9 +654,10 @@ "class WindTurbine(ControlEnvironment):\n", " \"A function that creates and runs the YawEnv environment for a wind turbine. Indexes 0 - action, 1 - yaw error, 2 - wind direction, 3 - wind speed (ignore 0).\"\n", " \n", - " def __init__(self, value=0, name=\"WindTurbine\", links=None, new_name=True, namespace=None, **cargs): \n", + " def __init__(self, value=0, name=\"WindTurbine\", links=None, new_name=True, namespace=None, seed=None, **cargs): \n", " super().__init__(value=value, links=links, name=name, new_name=new_name, namespace=namespace, **cargs)\n", " \n", + " self.zero_threshold = 0\n", " self.num_links=1\n", " self.env_name='YawEnv'\n", " self.env = YawEnv()\n", @@ -669,7 +670,8 @@ "\n", " def set_properties(self, props):\n", " self.env.initialise(props)\n", - " # wind_timeseries,start_index,stop_index,ancestors,filter_duration,yaw_parameters,\n", + " if 'zero_threshold' in props:\n", + " self.zero_threshold = props['zero_threshold']\n", "\n", " def early_terminate(self):\n", " pass\n", @@ -678,16 +680,16 @@ " self.input = self.links[0].get_value()\n", " \n", " def process_actions(self):\n", - " if self.input < 0:\n", + " if abs(self.input)<= self.zero_threshold: \n", + " self.action = 1 \n", + " elif self.input < 0:\n", " self.action = 0\n", " elif self.input > 0:\n", " self.action = 2\n", - " else:\n", - " self.action = 1 \n", - " \n", + " \n", " \n", " def apply_actions_get_obs(self):\n", - " return self.env.step(self.input)\n", + " return self.env.step(self.action)\n", "\n", " def parse_obs(self):\n", " self.value = self.obs[0][-1]\n", @@ -697,6 +699,7 @@ "\n", " def process_values(self):\n", " self.value = np.append(self.value, self.obs[1])\n", + " self.reward=-(self.reward-self.env.w2)\n", " pass\n", " # raise Exception(f'TBD {self.__class__.__name__}:{self.env_name}.')\n", "\n", @@ -711,6 +714,7 @@ " self.render=render\n", " \n", " def reset(self, full=True, seed=None): \n", + " self.zero_threshold = 0\n", " self.env.reset()\n", " # raise Exception(f'TBD {self.__class__.__name__}:{self.env_name}.')\n", "\n", diff --git a/nbs/07_errors.ipynb b/nbs/07_errors.ipynb index b340f560..4b2d5e69 100644 --- a/nbs/07_errors.ipynb +++ b/nbs/07_errors.ipynb @@ -156,6 +156,31 @@ " def create(self, flip_error_response=False): return RootMeanSquareError(flip_error_response=flip_error_response)" ] }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [], + "source": [ + "#| export\n", + "class SummedError(BaseErrorType):\n", + " \"Sum of all errors.\"\n", + " def __init__(self, flip_error_response=False):\n", + " super().__init__(flip_error_response=flip_error_response)\n", + " self.reset()\n", + " \n", + " def __call__(self, error):\n", + " self.sum+=error\n", + " self.error_response=self.sum\n", + "\n", + " def reset(self):\n", + " super().reset()\n", + " self.sum=0\n", + " \n", + " class Factory:\n", + " def create(self, flip_error_response=False): return SummedError(flip_error_response=flip_error_response)" + ] + }, { "cell_type": "code", "execution_count": null, diff --git a/nbs/12_yaw_module.ipynb b/nbs/12_yaw_module.ipynb index 762ea783..f561accf 100644 --- a/nbs/12_yaw_module.ipynb +++ b/nbs/12_yaw_module.ipynb @@ -266,7 +266,7 @@ " )\n", "\n", " self.ancestors = ancestors\n", - " print(self.episode_len, \" points in simulation dataset\")\n", + " # print(self.episode_len, \" points in simulation dataset\")\n", " self.action_space = Discrete(3)\n", "\n", " # Observation space : Represents environment **after yaw actuation**\n", diff --git a/pct/_modidx.py b/pct/_modidx.py index 816c8996..429b3ee0 100644 --- a/pct/_modidx.py +++ b/pct/_modidx.py @@ -422,6 +422,11 @@ 'pct.errors.SmoothError.__call__': ('errors.html#smootherror.__call__', 'pct/errors.py'), 'pct.errors.SmoothError.__init__': ('errors.html#smootherror.__init__', 'pct/errors.py'), 'pct.errors.SmoothError.reset': ('errors.html#smootherror.reset', 'pct/errors.py'), + 'pct.errors.SummedError': ('errors.html#summederror', 'pct/errors.py'), + 'pct.errors.SummedError.Factory': ('errors.html#summederror.factory', 'pct/errors.py'), + 'pct.errors.SummedError.__call__': ('errors.html#summederror.__call__', 'pct/errors.py'), + 'pct.errors.SummedError.__init__': ('errors.html#summederror.__init__', 'pct/errors.py'), + 'pct.errors.SummedError.reset': ('errors.html#summederror.reset', 'pct/errors.py'), 'pct.errors.TopError': ('errors.html#toperror', 'pct/errors.py'), 'pct.errors.TopError.Factory': ('errors.html#toperror.factory', 'pct/errors.py'), 'pct.errors.TopError.__init__': ('errors.html#toperror.__init__', 'pct/errors.py'), diff --git a/pct/environments.py b/pct/environments.py index 37a2039e..aaf2396e 100644 --- a/pct/environments.py +++ b/pct/environments.py @@ -508,9 +508,10 @@ def create(self, namespace=None, seed=None): return MountainCarContinuousV0(name class WindTurbine(ControlEnvironment): "A function that creates and runs the YawEnv environment for a wind turbine. Indexes 0 - action, 1 - yaw error, 2 - wind direction, 3 - wind speed (ignore 0)." - def __init__(self, value=0, name="WindTurbine", links=None, new_name=True, namespace=None, **cargs): + def __init__(self, value=0, name="WindTurbine", links=None, new_name=True, namespace=None, seed=None, **cargs): super().__init__(value=value, links=links, name=name, new_name=new_name, namespace=namespace, **cargs) + self.zero_threshold = 0 self.num_links=1 self.env_name='YawEnv' self.env = YawEnv() @@ -523,7 +524,8 @@ def __call__(self, verbose=False): def set_properties(self, props): self.env.initialise(props) - # wind_timeseries,start_index,stop_index,ancestors,filter_duration,yaw_parameters, + if 'zero_threshold' in props: + self.zero_threshold = props['zero_threshold'] def early_terminate(self): pass @@ -532,16 +534,16 @@ def process_inputs(self): self.input = self.links[0].get_value() def process_actions(self): - if self.input < 0: + if abs(self.input)<= self.zero_threshold: + self.action = 1 + elif self.input < 0: self.action = 0 elif self.input > 0: self.action = 2 - else: - self.action = 1 - + def apply_actions_get_obs(self): - return self.env.step(self.input) + return self.env.step(self.action) def parse_obs(self): self.value = self.obs[0][-1] @@ -551,6 +553,7 @@ def parse_obs(self): def process_values(self): self.value = np.append(self.value, self.obs[1]) + self.reward=-(self.reward-self.env.w2) pass # raise Exception(f'TBD {self.__class__.__name__}:{self.env_name}.') @@ -565,6 +568,7 @@ def set_render(self, render): self.render=render def reset(self, full=True, seed=None): + self.zero_threshold = 0 self.env.reset() # raise Exception(f'TBD {self.__class__.__name__}:{self.env_name}.') diff --git a/pct/errors.py b/pct/errors.py index 9ae5eedb..b4f53ace 100644 --- a/pct/errors.py +++ b/pct/errors.py @@ -1,9 +1,9 @@ # AUTOGENERATED! DO NOT EDIT! File to edit: ../nbs/07_errors.ipynb. # %% auto 0 -__all__ = ['BaseErrorType', 'RootSumSquaredError', 'RootMeanSquareError', 'CurrentError', 'SmoothError', 'BaseErrorCollector', - 'TotalError', 'TopError', 'InputsError', 'ReferencedInputsError', 'RewardError', 'ErrorResponseFactory', - 'ErrorCollectorFactory'] +__all__ = ['BaseErrorType', 'RootSumSquaredError', 'RootMeanSquareError', 'SummedError', 'CurrentError', 'SmoothError', + 'BaseErrorCollector', 'TotalError', 'TopError', 'InputsError', 'ReferencedInputsError', 'RewardError', + 'ErrorResponseFactory', 'ErrorCollectorFactory'] # %% ../nbs/07_errors.ipynb 3 #import numpy as np @@ -84,6 +84,24 @@ class Factory: def create(self, flip_error_response=False): return RootMeanSquareError(flip_error_response=flip_error_response) # %% ../nbs/07_errors.ipynb 8 +class SummedError(BaseErrorType): + "Sum of all errors." + def __init__(self, flip_error_response=False): + super().__init__(flip_error_response=flip_error_response) + self.reset() + + def __call__(self, error): + self.sum+=error + self.error_response=self.sum + + def reset(self): + super().reset() + self.sum=0 + + class Factory: + def create(self, flip_error_response=False): return SummedError(flip_error_response=flip_error_response) + +# %% ../nbs/07_errors.ipynb 9 class CurrentError(BaseErrorType): "The current error, rather than a function of the historical values." def __init__(self, flip_error_response=False): @@ -98,7 +116,7 @@ def reset(self): class Factory: def create(self, flip_error_response=False): return CurrentError(flip_error_response=flip_error_response) -# %% ../nbs/07_errors.ipynb 9 +# %% ../nbs/07_errors.ipynb 10 class SmoothError(BaseErrorType): "The exponential smoothed value of the error." def __init__(self, flip_error_response=False): @@ -115,7 +133,7 @@ def reset(self): class Factory: def create(self, flip_error_response=False): return SmoothError(flip_error_response=flip_error_response) -# %% ../nbs/07_errors.ipynb 10 +# %% ../nbs/07_errors.ipynb 11 class BaseErrorCollector(ABC): "Base class of an error collector. This class is not used direclty by developers, but defines the interface common to all." 'Parameters:' @@ -191,7 +209,7 @@ def check_limit(self): return self.limit_exceeded -# %% ../nbs/07_errors.ipynb 11 +# %% ../nbs/07_errors.ipynb 12 class TotalError(BaseErrorCollector): "A class to collect all the errors of the control system run." def __init__(self, limit=1000, error_response=None, min=None, **cargs): @@ -209,7 +227,7 @@ def add_data(self, hpct=None): class Factory: def create(self): return TotalError() -# %% ../nbs/07_errors.ipynb 12 +# %% ../nbs/07_errors.ipynb 13 class TopError(BaseErrorCollector): "A class to collect all the errors of the top-level nodes." def __init__(self, limit=1000, error_response=None, min=None, **cargs): @@ -229,7 +247,7 @@ def add_data(self, hpct=None): class Factory: def create(self): return TopError() -# %% ../nbs/07_errors.ipynb 13 +# %% ../nbs/07_errors.ipynb 14 class InputsError(BaseErrorCollector): "A class to collect the values of the input values." def __init__(self, limit=1000, error_response=None, min=None, **cargs): @@ -250,7 +268,7 @@ def add_data(self, hpct=None): class Factory: def create(self): return InputsError() -# %% ../nbs/07_errors.ipynb 14 +# %% ../nbs/07_errors.ipynb 15 class ReferencedInputsError(BaseErrorCollector): "A class to collect the values of the input values subtracted from reference values." def __init__(self, limit=1000, error_response=None, min=None, **cargs): @@ -288,7 +306,7 @@ def add_data(self, hpct=None): class Factory: def create(self): return ReferencedInputsError() -# %% ../nbs/07_errors.ipynb 15 +# %% ../nbs/07_errors.ipynb 16 class RewardError(BaseErrorCollector): "A class that collects the reward value of the control system run." def __init__(self, limit=1000, error_response=None, min=None, **cargs): @@ -304,7 +322,7 @@ def add_data(self, hpct=None): class Factory: def create(self): return RewardError() -# %% ../nbs/07_errors.ipynb 16 +# %% ../nbs/07_errors.ipynb 17 class ErrorResponseFactory: factories = {} def addResponseFactory(id, errorResponseFactory): @@ -318,7 +336,7 @@ def createErrorResponse(id, flip_error_response=False): return ErrorResponseFactory.factories[id].create(flip_error_response=flip_error_response) createErrorResponse = staticmethod(createErrorResponse) -# %% ../nbs/07_errors.ipynb 17 +# %% ../nbs/07_errors.ipynb 18 class ErrorCollectorFactory: factories = {} def addCollectorFactory(id, errorCollectorFactory): diff --git a/pct/yaw_module.py b/pct/yaw_module.py index e06bd216..0b080dc5 100644 --- a/pct/yaw_module.py +++ b/pct/yaw_module.py @@ -194,7 +194,7 @@ def initialise(self, properties ): ) self.ancestors = ancestors - print(self.episode_len, " points in simulation dataset") + # print(self.episode_len, " points in simulation dataset") self.action_space = Discrete(3) # Observation space : Represents environment **after yaw actuation** From 72596241914be400c6fc93257c5d71604d0587a8 Mon Sep 17 00:00:00 2001 From: perceptualrobots Date: Wed, 9 Aug 2023 17:19:03 +0100 Subject: [PATCH 6/6] update --- nbs/12_yaw_module.ipynb | 71 ++++++++++++++++++++++++++++++++++++++++ pct/_modidx.py | 3 +- pct/yaw_module.py | 72 ++++++++++++++++++++++++++++++++++++++--- 3 files changed, 141 insertions(+), 5 deletions(-) diff --git a/nbs/12_yaw_module.ipynb b/nbs/12_yaw_module.ipynb index f561accf..ca0a4abe 100644 --- a/nbs/12_yaw_module.ipynb +++ b/nbs/12_yaw_module.ipynb @@ -223,6 +223,77 @@ " return wind_timeseries,model_params['start_index'], model_params['stop_index'], model_params['ancestors'], model_params['filter_duration'],yaw_params,keep_history" ] }, + { + "cell_type": "code", + "execution_count": null, + "id": "ef00fec4", + "metadata": {}, + "outputs": [], + "source": [ + "#| export\n", + "def test_trad_control(wind_timeseries, wind_timeseries_not_agg,agg, start, end, experiment=None,datatype='baseline_simu'):\n", + " '''\n", + " test CYCA-S and CYCA-L\n", + "\n", + " '''\n", + " fig, ax = plt.subplots(figsize=(15, 5))\n", + " ax.plot(range(0,(end-start)*10,10), wind_timeseries[\"wind_direction\"][start:end], label=\"wind direction (deg)\")\n", + " ax.plot(range(0,(end-start)*10,10), wind_timeseries[\"nacelle_pos_\" + datatype][start:end], label=\"nacelle position (deg)\")\n", + " if experiment:\n", + " experiment.log_curve(\n", + " \"wind_direction\",\n", + " range(0, end-start),\n", + " wind_timeseries[\"wind_direction\"][start:end],\n", + " overwrite = True,\n", + " )\n", + " if experiment:\n", + " experiment.log_curve(\n", + " \"nacelle_pos_\"+datatype,\n", + " range(0, end-start),\n", + " wind_timeseries[\"nacelle_pos_\" + datatype][start:end],\n", + " overwrite = True,\n", + " )\n", + "\n", + " plt.legend()\n", + " plotly_fig = tls.mpl_to_plotly(fig)\n", + " plotly_fig.write_html(\"res.html\")\n", + "\n", + " if experiment:\n", + " experiment.log_html(open(\"res.html\").read())\n", + "\n", + " average_yaw_error = (oriented_angle(wind_timeseries[\"wind_direction\"][start:end] - wind_timeseries[\"nacelle_pos_\" + datatype][start:end]).abs().mean())\n", + " nacelle_position_diff = oriented_angle(wind_timeseries[\"nacelle_pos_\" + datatype][start:end].diff(1).dropna())\n", + " nacelle_position_not_agg_diff = oriented_angle(wind_timeseries_not_agg[\"nacelle_pos_\" + datatype][start*agg:end*agg].diff(1).dropna())\n", + " angle_covered = sum(abs(nacelle_position_diff))\n", + " yaw_count = get_yaw_count(nacelle_position_diff.to_list())\n", + " time_yawing = get_time_yawing(nacelle_position_not_agg_diff.to_list())\n", + "\n", + " if experiment:\n", + " experiment.log_metrics(\n", + " {\n", + " \"start_trad\": start,\n", + " \"end_trad\": end,\n", + " \"average yaw error_\"+ datatype: average_yaw_error,\n", + " \"angle covered_trad_\"+ datatype: angle_covered,\n", + " \"yaw count_trad_\"+ datatype: yaw_count,\n", + " \"time_yawing_trad_\"+ datatype: time_yawing,\n", + " }\n", + " )\n", + "\n", + " return {\n", + " \"start\": start,\n", + " \"end\": end,\n", + " \"average yaw error_\"+ datatype: average_yaw_error,\n", + " \"angle covered_trad_\"+ datatype: angle_covered,\n", + " \"yaw count_trad_\"+ datatype: yaw_count,\n", + " \"time_yawing_trad_\"+ datatype: time_yawing,\n", + " }, \\\n", + " wind_timeseries[\"nacelle_pos_\" + datatype][start:end].to_list(), \\\n", + " wind_timeseries[\"wind_direction\"][start:end].to_list()\n", + " \n", + "\n" + ] + }, { "cell_type": "code", "execution_count": null, diff --git a/pct/_modidx.py b/pct/_modidx.py index 429b3ee0..88ffa3e7 100644 --- a/pct/_modidx.py +++ b/pct/_modidx.py @@ -980,4 +980,5 @@ 'pct.yaw_module.get_time_yawing': ('yaw_module.html#get_time_yawing', 'pct/yaw_module.py'), 'pct.yaw_module.get_yaw_count': ('yaw_module.html#get_yaw_count', 'pct/yaw_module.py'), 'pct.yaw_module.oriented_angle': ('yaw_module.html#oriented_angle', 'pct/yaw_module.py'), - 'pct.yaw_module.test_model_wind': ('yaw_module.html#test_model_wind', 'pct/yaw_module.py')}}} + 'pct.yaw_module.test_model_wind': ('yaw_module.html#test_model_wind', 'pct/yaw_module.py'), + 'pct.yaw_module.test_trad_control': ('yaw_module.html#test_trad_control', 'pct/yaw_module.py')}}} diff --git a/pct/yaw_module.py b/pct/yaw_module.py index 0b080dc5..4bec3127 100644 --- a/pct/yaw_module.py +++ b/pct/yaw_module.py @@ -1,8 +1,8 @@ # AUTOGENERATED! DO NOT EDIT! File to edit: ../nbs/12_yaw_module.ipynb. # %% auto 0 -__all__ = ['get_yaw_count', 'get_time_yawing', 'oriented_angle', 'get_dataset_from_simu', 'get_properties', 'YawEnv', - 'get_comparaison_metrics', 'test_model_wind'] +__all__ = ['get_yaw_count', 'get_time_yawing', 'oriented_angle', 'get_dataset_from_simu', 'get_properties', 'test_trad_control', + 'YawEnv', 'get_comparaison_metrics', 'test_model_wind'] # %% ../nbs/12_yaw_module.ipynb 2 import warnings @@ -159,6 +159,70 @@ def get_properties(properties): return wind_timeseries,model_params['start_index'], model_params['stop_index'], model_params['ancestors'], model_params['filter_duration'],yaw_params,keep_history # %% ../nbs/12_yaw_module.ipynb 8 +def test_trad_control(wind_timeseries, wind_timeseries_not_agg,agg, start, end, experiment=None,datatype='baseline_simu'): + ''' + test CYCA-S and CYCA-L + + ''' + fig, ax = plt.subplots(figsize=(15, 5)) + ax.plot(range(0,(end-start)*10,10), wind_timeseries["wind_direction"][start:end], label="wind direction (deg)") + ax.plot(range(0,(end-start)*10,10), wind_timeseries["nacelle_pos_" + datatype][start:end], label="nacelle position (deg)") + if experiment: + experiment.log_curve( + "wind_direction", + range(0, end-start), + wind_timeseries["wind_direction"][start:end], + overwrite = True, + ) + if experiment: + experiment.log_curve( + "nacelle_pos_"+datatype, + range(0, end-start), + wind_timeseries["nacelle_pos_" + datatype][start:end], + overwrite = True, + ) + + plt.legend() + plotly_fig = tls.mpl_to_plotly(fig) + plotly_fig.write_html("res.html") + + if experiment: + experiment.log_html(open("res.html").read()) + + average_yaw_error = (oriented_angle(wind_timeseries["wind_direction"][start:end] - wind_timeseries["nacelle_pos_" + datatype][start:end]).abs().mean()) + nacelle_position_diff = oriented_angle(wind_timeseries["nacelle_pos_" + datatype][start:end].diff(1).dropna()) + nacelle_position_not_agg_diff = oriented_angle(wind_timeseries_not_agg["nacelle_pos_" + datatype][start*agg:end*agg].diff(1).dropna()) + angle_covered = sum(abs(nacelle_position_diff)) + yaw_count = get_yaw_count(nacelle_position_diff.to_list()) + time_yawing = get_time_yawing(nacelle_position_not_agg_diff.to_list()) + + if experiment: + experiment.log_metrics( + { + "start_trad": start, + "end_trad": end, + "average yaw error_"+ datatype: average_yaw_error, + "angle covered_trad_"+ datatype: angle_covered, + "yaw count_trad_"+ datatype: yaw_count, + "time_yawing_trad_"+ datatype: time_yawing, + } + ) + + return { + "start": start, + "end": end, + "average yaw error_"+ datatype: average_yaw_error, + "angle covered_trad_"+ datatype: angle_covered, + "yaw count_trad_"+ datatype: yaw_count, + "time_yawing_trad_"+ datatype: time_yawing, + }, \ + wind_timeseries["nacelle_pos_" + datatype][start:end].to_list(), \ + wind_timeseries["wind_direction"][start:end].to_list() + + + + +# %% ../nbs/12_yaw_module.ipynb 9 class YawEnv(Env): def initialise(self, properties ): @@ -351,7 +415,7 @@ def reset(self): return self.state -# %% ../nbs/12_yaw_module.ipynb 9 +# %% ../nbs/12_yaw_module.ipynb 10 def get_comparaison_metrics(wind_direction,power_control,power_simu,res_model, res_baseline_simu, yaw_rate, yaw_power, width_bin) : res_model_diff = pd.Series(res_model).diff(1).fillna(0) res_baseline_simu_diff = pd.Series(res_baseline_simu).diff(1).fillna(0) @@ -387,7 +451,7 @@ def get_comparaison_metrics(wind_direction,power_control,power_simu,res_model, r -# %% ../nbs/12_yaw_module.ipynb 10 +# %% ../nbs/12_yaw_module.ipynb 11 def test_model_wind(wind_timeseries,start_index,stop_index,ancestors,filter_duration,yaw_parameters,experiment=None,datatype='test'): ''' test RLYCA