Skip to content

Commit 20fd3a6

Browse files
committed
Starting refactor
1 parent 08d2594 commit 20fd3a6

3 files changed

Lines changed: 7 additions & 23 deletions

File tree

README.md

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -35,7 +35,7 @@ The main processing pipeline of the wristpy module can be described as follows:
3535
- **Data calibration**: A post-manufacturer calibration step can be applied, to ensure that the acceleration sensor is measuring 1*g* force during periods of no motion. There are three possible options: `None`, `gradient`, `ggir`.
3636
- ***Data imputation*** In the special case when dealing with the Actigraph `idle_sleep_mode == enabled`, the gaps in acceleration are filled in after calibration, to avoid biasing the calibration phase.
3737
- **Metrics Calculation**: Calculates various activity metrics on the calibrated data, namely ENMO (Euclidean norm, minus one), MAD (mean amplitude deviation) <sup>1</sup>, Actigraph activity counts<sup>2</sup>, MIMS (monitor-independent movement summary) unit <sup>3</sup>, and angle-Z (angle of acceleration relative to the *x-y* axis).
38-
- **Non-wear detection**: We find periods of non-wear based on the acceleration data. Specifically, the standard deviation of the acceleration values in a given time window, along each axis, is used as a threshold to decide `wear` or `not wear`. Additionally, we can use the temperature sensor, when avaia\lable, to augment the acceleration data. This is used in the CTA (combined temperature and acceleration) algorithm <sup>4</sup>, and in the `skdh` DETACH algorithm <sup>5</sup>. Furthermore, ensemble classification of non-wear periods is possible by providing a list (of any length) of non-wear algorithm options.
38+
- **Non-wear detection**: We find periods of non-wear based on the acceleration data. Specifically, the standard deviation of the acceleration values in a given time window, along each axis, is used as a threshold to decide `wear` or `not wear`. Additionally, we can use the temperature sensor, when avaialable, to augment the acceleration data. This is used in the CTA (combined temperature and acceleration) algorithm <sup>4</sup>, and in the DETACH algorithm <sup>5</sup>. Furthermore, ensemble classification of non-wear periods is possible by providing a list (of any length) of non-wear algorithm options.
3939
- **Sleep Detection**: Using the HDCZ<sup>6</sup> and HSPT<sup>7</sup> algorithms to analyze changes in arm angle we are able to find periods of sleep. We find the sleep onset-wakeup times for all sleep windows detected. Any sleep periods that overlap with detected non-wear times are removed, and any remaining sleep periods shorter than 15 minutes (default value) are removed. Additionally, the SIB (sustained inactivity bouts) and the SPT (sleep period time) windows are provided as part of the output to aid in sleep metric post-processing.
4040
- **Physical activity levels**: Using the chosen physical activity metric (aggregated into time bins, 5 second default) we compute activity levels into the following categories: [`inactive`, `light`, `moderate`, `vigorous`]. The threshold values can be defined by the user, while the default values are chosen based on the specific activity metric and the values found in the literature <sup>8-10</sup>.
4141
- **Data output**: The output results can be saved in `.csv` or `.parquet` data formats, with the run-time configuration parameters saved in a `.json` dictionary.
Lines changed: 4 additions & 20 deletions
Original file line numberDiff line numberDiff line change
@@ -33,7 +33,7 @@
3333
from scipy import signal
3434

3535

36-
def nimbaldetach(
36+
def detach(
3737
x_values: np.ndarray,
3838
y_values: np.ndarray,
3939
z_values: np.ndarray,
@@ -73,16 +73,9 @@ def nimbaldetach(
7373
7474
7575
Returns:
76-
A tuple with (start_stop_df, vert_nonwear_array) as defined below:
77-
78-
start_stop_df: A dataframe with the start and end datapoints of non-wear.
79-
vert_nonwear_array: numpy array with length of the accelerometer data marked as
76+
A numpy array with length of the accelerometer data marked as
8077
either wear (0) or non-wear (1).
8178
"""
82-
vert_nonwear_array = np.zeros(len(x_values))
83-
vert_nonwear_start_datapoints = []
84-
vert_nonwear_end_datapoints = []
85-
8679
x_std_fwd = pd.Series(x_values)[::-1].rolling(round(accel_freq * 60)).std()[::-1]
8780
y_std_fwd = pd.Series(y_values)[::-1].rolling(round(accel_freq * 60)).std()[::-1]
8881
z_std_fwd = pd.Series(z_values)[::-1].rolling(round(accel_freq * 60)).std()[::-1]
@@ -197,6 +190,7 @@ def nimbaldetach(
197190

198191
end_crit_combined = np.sort(np.unique(np.concatenate((end_crit_1, end_crit_2))))
199192

193+
vert_nonwear_array = np.zeros(len(x_values))
200194
previous_end = 0
201195
for ind in candidate_nw_starts[0]:
202196
if ind < previous_end:
@@ -226,20 +220,10 @@ def nimbaldetach(
226220
accel_start_dp = int(start_ind * accel_freq / temperature_freq)
227221
accel_end_dp = int(bout_end_index * accel_freq / temperature_freq)
228222
vert_nonwear_array[accel_start_dp:accel_end_dp] = 1
229-
vert_nonwear_start_datapoints.append(accel_start_dp)
230-
vert_nonwear_end_datapoints.append(accel_end_dp)
231223

232224
previous_end = bout_end_index
233225

234-
start_stop_df = pd.DataFrame(
235-
{
236-
"Start Datapoint": vert_nonwear_start_datapoints,
237-
"End Datapoint": vert_nonwear_end_datapoints,
238-
},
239-
index=range(1, len(vert_nonwear_start_datapoints) + 1),
240-
)
241-
242-
return start_stop_df, vert_nonwear_array
226+
return vert_nonwear_array
243227

244228

245229
def _lowpass_filter_signal(

src/wristpy/processing/metrics.py

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -7,7 +7,7 @@
77
from scipy import interpolate, signal
88

99
from wristpy.core import computations, config, models
10-
from wristpy.processing import mims, nimbaldetach
10+
from wristpy.processing import _nimbaldetach, mims
1111

1212
logger = config.get_logger()
1313

@@ -421,7 +421,7 @@ def cleanup_DETACH_nonwear(nonwear: models.Measurement) -> models.Measurement:
421421
1 / ((acceleration.time[1:] - acceleration.time[:-1]).median()).total_seconds() # type: ignore[union-attr] #Guarded by Measurement validation for .time attribute
422422
)
423423

424-
[deatch_wear, nonwear_array] = nimbaldetach.nimbaldetach(
424+
[deatch_wear, nonwear_array] = _nimbaldetach.detach(
425425
x_values=acceleration.measurements[:, 0],
426426
y_values=acceleration.measurements[:, 1],
427427
z_values=acceleration.measurements[:, 2],

0 commit comments

Comments
 (0)