apmtools 0.2.36__tar.gz → 0.2.38__tar.gz
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- {apmtools-0.2.36 → apmtools-0.2.38}/PKG-INFO +1 -1
- {apmtools-0.2.36 → apmtools-0.2.38}/pyproject.toml +1 -1
- {apmtools-0.2.36 → apmtools-0.2.38}/src/apmtools/classes.py +98 -88
- {apmtools-0.2.36 → apmtools-0.2.38}/src/apmtools/data_processing.py +9 -2
- {apmtools-0.2.36 → apmtools-0.2.38}/src/apmtools/shiny/summary.py +6 -6
- {apmtools-0.2.36 → apmtools-0.2.38}/.gitignore +0 -0
- {apmtools-0.2.36 → apmtools-0.2.38}/LICENSE +0 -0
- {apmtools-0.2.36 → apmtools-0.2.38}/README.md +0 -0
- {apmtools-0.2.36 → apmtools-0.2.38}/src/apmtools/__init__.py +0 -0
- {apmtools-0.2.36 → apmtools-0.2.38}/src/apmtools/functions.py +0 -0
- {apmtools-0.2.36 → apmtools-0.2.38}/src/apmtools/legacy.py +0 -0
- {apmtools-0.2.36 → apmtools-0.2.38}/src/apmtools/shiny/__init__.py +0 -0
- {apmtools-0.2.36 → apmtools-0.2.38}/src/apmtools/units.py +0 -0
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
Metadata-Version: 2.5
|
|
2
2
|
Name: apmtools
|
|
3
|
-
Version: 0.2.
|
|
3
|
+
Version: 0.2.38
|
|
4
4
|
Summary: A collection of tools for processing air pollution monitoring data
|
|
5
5
|
Project-URL: Homepage, https://github.com/federlorenz/apmtools
|
|
6
6
|
Author-email: Federico Lorenzetti <lorenzetti.federico@gmail.com>
|
|
@@ -453,9 +453,9 @@ class Dataset(DictionaryPlus):
|
|
|
453
453
|
|
|
454
454
|
from .data_processing import upas_processing, lascar_processing, purple_processing, lcm_processing
|
|
455
455
|
|
|
456
|
-
if len(set(levels).intersection(set(["identifier", "start", "end", "length", "
|
|
456
|
+
if len(set(levels).intersection(set(["identifier", "start", "end", "length", "datetime", "timedelta","pm25", "pm25correctedrh", "pm25correctedrhandgrav", "filterid", "grav_not", "grav","PM2.5","PM10","C02","NO2"]))) > 0:
|
|
457
457
|
print(
|
|
458
|
-
f"the following levels names are not allowed: {set(levels).intersection(set(["identifier", "start", "end", "length", "
|
|
458
|
+
f"the following levels names are not allowed: {set(levels).intersection(set(["identifier", "start", "end", "length", "datetime", "timedelta", "pm25", "pm25correctedrh", "pm25correctedrhandgrav", "filterid", "grav_not", "grav","PM2.5","PM10","C02","NO2"]))}. Please choose different level names")
|
|
459
459
|
return
|
|
460
460
|
if levels_dict == None:
|
|
461
461
|
levels_dict = dict(
|
|
@@ -608,7 +608,7 @@ class Dataset(DictionaryPlus):
|
|
|
608
608
|
c = 5.75
|
|
609
609
|
d = self.subset(condition=lambda x: match_monitor(x) == "Upas")
|
|
610
610
|
columns1 = ["identifier", "monitor",
|
|
611
|
-
"start", "end", "length", "
|
|
611
|
+
"start", "end", "length", "datetime","timedelta"]
|
|
612
612
|
columns2 = list(set(d.meta()).difference(
|
|
613
613
|
set(["filter", "header", "parameters"])))
|
|
614
614
|
if "upas" not in columns.keys():
|
|
@@ -644,6 +644,7 @@ class Dataset(DictionaryPlus):
|
|
|
644
644
|
app.append(end)
|
|
645
645
|
app.append(length)
|
|
646
646
|
app.append(v.index[i])
|
|
647
|
+
app.append(v.index[i]-v.start)
|
|
647
648
|
for m in columns2:
|
|
648
649
|
if m in v.m.keys():
|
|
649
650
|
app.append(v.m[m] if v.m[m] != None else "")
|
|
@@ -677,13 +678,14 @@ class Dataset(DictionaryPlus):
|
|
|
677
678
|
out["start"] = pd.to_datetime(out["start"])
|
|
678
679
|
out["end"] = pd.to_datetime(out["end"])
|
|
679
680
|
out["length"] = pd.to_timedelta(out["length"])
|
|
680
|
-
out["
|
|
681
|
+
out["datetime"] = pd.to_datetime(out["datetime"])
|
|
682
|
+
out["timedelta"] = pd.to_timedelta(out["timedelta"])
|
|
681
683
|
return (Summary(out, metadata=set(columns2)))
|
|
682
684
|
|
|
683
685
|
def run_lascar():
|
|
684
686
|
d = self.subset(condition=lambda x: match_monitor(x) == "Lascar")
|
|
685
687
|
columns1 = ["identifier", "monitor",
|
|
686
|
-
"start", "end", "length", "
|
|
688
|
+
"start", "end", "length", "datetime", "timedelta"]
|
|
687
689
|
columns2 = list(set(d.meta()))
|
|
688
690
|
columns3 = ["CO(ppm)"]
|
|
689
691
|
|
|
@@ -707,6 +709,7 @@ class Dataset(DictionaryPlus):
|
|
|
707
709
|
app.append(end)
|
|
708
710
|
app.append(length)
|
|
709
711
|
app.append(v.index[i])
|
|
712
|
+
app.append(v.index[i]-v.start)
|
|
710
713
|
for m in columns2:
|
|
711
714
|
if m in v.m.keys():
|
|
712
715
|
app.append(v.m[m] if v.m[m] != None else "")
|
|
@@ -720,7 +723,8 @@ class Dataset(DictionaryPlus):
|
|
|
720
723
|
out["start"] = pd.to_datetime(out["start"])
|
|
721
724
|
out["end"] = pd.to_datetime(out["end"])
|
|
722
725
|
out["length"] = pd.to_timedelta(out["length"])
|
|
723
|
-
out["
|
|
726
|
+
out["datetime"] = pd.to_datetime(out["datetime"])
|
|
727
|
+
out["timedelta"] = pd.to_timedelta(out["timedelta"])
|
|
724
728
|
return (Summary(out, metadata=set(columns2)))
|
|
725
729
|
|
|
726
730
|
def run_lcm():
|
|
@@ -729,7 +733,7 @@ class Dataset(DictionaryPlus):
|
|
|
729
733
|
c = 5.75
|
|
730
734
|
d = self.subset(condition=lambda x: match_monitor(x) == "Lcm")
|
|
731
735
|
columns1 = ["identifier", "monitor",
|
|
732
|
-
"start", "end", "length", "
|
|
736
|
+
"start", "end", "length", "datetime", "timedelta"]
|
|
733
737
|
columns2 = list(set(d.meta()))
|
|
734
738
|
columns3 = ["sensorName", "deviceId", "resolution",
|
|
735
739
|
"PM2.5", "PM10", "CO2", "NO2", "Temperature", "Humidity"]
|
|
@@ -755,6 +759,7 @@ class Dataset(DictionaryPlus):
|
|
|
755
759
|
app.append(end)
|
|
756
760
|
app.append(length)
|
|
757
761
|
app.append(v.index[i])
|
|
762
|
+
app.append(v.index[i]-v.start)
|
|
758
763
|
for m in columns2:
|
|
759
764
|
if m in v.m.keys():
|
|
760
765
|
app.append(v.m[m] if v.m[m] != None else "")
|
|
@@ -771,13 +776,14 @@ class Dataset(DictionaryPlus):
|
|
|
771
776
|
out["start"] = pd.to_datetime(out["start"])
|
|
772
777
|
out["end"] = pd.to_datetime(out["end"])
|
|
773
778
|
out["length"] = pd.to_timedelta(out["length"])
|
|
774
|
-
out["
|
|
779
|
+
out["datetime"] = pd.to_datetime(out["datetime"])
|
|
780
|
+
out["timedelta"] = pd.to_timedelta(out["timedelta"])
|
|
775
781
|
return (Summary(out, metadata=set(columns2)))
|
|
776
782
|
|
|
777
783
|
def run_purple():
|
|
778
784
|
d = self.subset(condition=lambda x: match_monitor(x) == "Purple")
|
|
779
785
|
columns1 = ["identifier", "monitor",
|
|
780
|
-
"start", "end", "length", "
|
|
786
|
+
"start", "end", "length", "datetime", "timedelta"]
|
|
781
787
|
columns2 = list(set(d.meta()))
|
|
782
788
|
columns3 = ["pm2_5", "pm2_5_adj"]
|
|
783
789
|
columns4 = []
|
|
@@ -806,6 +812,7 @@ class Dataset(DictionaryPlus):
|
|
|
806
812
|
app.append(end)
|
|
807
813
|
app.append(length)
|
|
808
814
|
app.append(v.index[i])
|
|
815
|
+
app.append(v.index[i]-v.start)
|
|
809
816
|
for m in columns2:
|
|
810
817
|
if m in v.m.keys():
|
|
811
818
|
app.append(v.m[m] if v.m[m] != None else "")
|
|
@@ -834,7 +841,8 @@ class Dataset(DictionaryPlus):
|
|
|
834
841
|
out["start"] = pd.to_datetime(out["start"])
|
|
835
842
|
out["end"] = pd.to_datetime(out["end"])
|
|
836
843
|
out["length"] = pd.to_timedelta(out["length"])
|
|
837
|
-
out["
|
|
844
|
+
out["datetime"] = pd.to_datetime(out["datetime"])
|
|
845
|
+
out["timedelta"] = pd.to_timedelta(out["timedelta"])
|
|
838
846
|
return (Summary(out, metadata=set(columns2)))
|
|
839
847
|
|
|
840
848
|
out = {}
|
|
@@ -1124,24 +1132,26 @@ class Summary(pd.DataFrame):
|
|
|
1124
1132
|
date_end = parse(date_end)
|
|
1125
1133
|
|
|
1126
1134
|
if date_start is not None:
|
|
1127
|
-
self = self.loc[self["
|
|
1135
|
+
self = self.loc[self["datetime"] >= date_start]
|
|
1128
1136
|
if date_end is not None:
|
|
1129
|
-
self = self.loc[self["
|
|
1137
|
+
self = self.loc[self["datetime"] < date_end]
|
|
1130
1138
|
if (time_start is not None) & (time_end is not None):
|
|
1131
1139
|
if time_start > time_end:
|
|
1132
|
-
self = self.loc[(self["
|
|
1133
|
-
| (self["
|
|
1140
|
+
self = self.loc[(self["datetime"].map(lambda x:x.time()) >= time_start)
|
|
1141
|
+
| (self["datetime"].map(lambda x: x.time()) < time_end)]
|
|
1134
1142
|
else:
|
|
1135
|
-
self = self.loc[(self["
|
|
1136
|
-
& (self["
|
|
1143
|
+
self = self.loc[(self["datetime"].map(lambda x: x.time()) >= time_start)
|
|
1144
|
+
& (self["datetime"].map(lambda x: x.time()) < time_end)]
|
|
1137
1145
|
if (time_start is not None) & (time_end is None):
|
|
1138
|
-
self = self.loc[self["
|
|
1146
|
+
self = self.loc[self["datetime"].map(
|
|
1147
|
+
lambda x: x.time()) >= time_start]
|
|
1139
1148
|
if (time_start is None) & (time_end is not None):
|
|
1140
|
-
self = self.loc[self["
|
|
1149
|
+
self = self.loc[self["datetime"].map(
|
|
1150
|
+
lambda x: x.time()) <= time_end]
|
|
1141
1151
|
|
|
1142
1152
|
if day is not None:
|
|
1143
|
-
self = self.loc[[a in day for a in [self["
|
|
1144
|
-
for i in range(len(self["
|
|
1153
|
+
self = self.loc[[a in day for a in [self["datetime"].map(lambda x: x.date().isoweekday())
|
|
1154
|
+
for i in range(len(self["datetime"]))]]]
|
|
1145
1155
|
return self.reset_index()
|
|
1146
1156
|
|
|
1147
1157
|
def set_attrib(self, attribute):
|
|
@@ -1216,27 +1226,27 @@ class Summary(pd.DataFrame):
|
|
|
1216
1226
|
case "hour":
|
|
1217
1227
|
expected = (pd.Timedelta(1, "hour") /
|
|
1218
1228
|
intervals).round().astype(int)
|
|
1219
|
-
df["xxxyyyxxx"] = df["
|
|
1229
|
+
df["xxxyyyxxx"] = df["datetime"].dt.floor("h")
|
|
1220
1230
|
case "day":
|
|
1221
1231
|
expected = (pd.Timedelta(1, "day") /
|
|
1222
1232
|
intervals).round().astype(int)
|
|
1223
|
-
df["xxxyyyxxx"] = df["
|
|
1233
|
+
df["xxxyyyxxx"] = df["datetime"].dt.floor("d")
|
|
1224
1234
|
case "minute":
|
|
1225
1235
|
expected = (pd.Timedelta(1, "minute") /
|
|
1226
1236
|
intervals).round().astype(int)
|
|
1227
|
-
df["xxxyyyxxx"] = df["
|
|
1237
|
+
df["xxxyyyxxx"] = df["datetime"].dt.floor("min")
|
|
1228
1238
|
case "second":
|
|
1229
1239
|
expected = (pd.Timedelta(1, "second") /
|
|
1230
1240
|
intervals).round().astype(int)
|
|
1231
|
-
df["xxxyyyxxx"] = df["
|
|
1241
|
+
df["xxxyyyxxx"] = df["datetime"].dt.floor("s")
|
|
1232
1242
|
case "week":
|
|
1233
1243
|
expected = (pd.Timedelta(1, "W") /
|
|
1234
1244
|
intervals).round().astype(int)
|
|
1235
|
-
df["xxxyyyxxx"] = df["
|
|
1245
|
+
df["xxxyyyxxx"] = df["datetime"].dt.floor("w")
|
|
1236
1246
|
case "weekday":
|
|
1237
1247
|
expected = (pd.Timedelta(1, "day") /
|
|
1238
1248
|
intervals).round().astype(int)
|
|
1239
|
-
df["xxxyyyxxx"] = df["
|
|
1249
|
+
df["xxxyyyxxx"] = df["datetime"].map(
|
|
1240
1250
|
lambda x: (x.weekday()))
|
|
1241
1251
|
if len(frequency.split(" ")) == 2:
|
|
1242
1252
|
mult = float(frequency.split(" ")[0])
|
|
@@ -1244,32 +1254,32 @@ class Summary(pd.DataFrame):
|
|
|
1244
1254
|
case "hour":
|
|
1245
1255
|
expected = (pd.Timedelta(mult, "hour") /
|
|
1246
1256
|
intervals).round().astype(int)
|
|
1247
|
-
df["xxxyyyxxx"] = df["
|
|
1257
|
+
df["xxxyyyxxx"] = df["datetime"].dt.floor(
|
|
1248
1258
|
f"{mult}h")
|
|
1249
1259
|
case "day":
|
|
1250
1260
|
expected = (pd.Timedelta(mult, "day") /
|
|
1251
1261
|
intervals).round().astype(int)
|
|
1252
|
-
df["xxxyyyxxx"] = df["
|
|
1262
|
+
df["xxxyyyxxx"] = df["datetime"].dt.floor(
|
|
1253
1263
|
f"{mult}d")
|
|
1254
1264
|
case "minute":
|
|
1255
1265
|
expected = (pd.Timedelta(mult, "minute") /
|
|
1256
1266
|
intervals).round().astype(int)
|
|
1257
|
-
df["xxxyyyxxx"] = df["
|
|
1267
|
+
df["xxxyyyxxx"] = df["datetime"].dt.floor(
|
|
1258
1268
|
f"{mult}min")
|
|
1259
1269
|
case "second":
|
|
1260
1270
|
expected = (pd.Timedelta(mult, "second") /
|
|
1261
1271
|
intervals).round().astype(int)
|
|
1262
|
-
df["xxxyyyxxx"] = df["
|
|
1272
|
+
df["xxxyyyxxx"] = df["datetime"].dt.floor(
|
|
1263
1273
|
f"{mult}s")
|
|
1264
1274
|
case "week":
|
|
1265
1275
|
expected = (pd.Timedelta(mult, "W") /
|
|
1266
1276
|
intervals).round().astype(int)
|
|
1267
|
-
df["xxxyyyxxx"] = df["
|
|
1277
|
+
df["xxxyyyxxx"] = df["datetime"].dt.floor(
|
|
1268
1278
|
f"{mult}w")
|
|
1269
1279
|
case "weekday":
|
|
1270
1280
|
expected = (pd.Timedelta(mult, "day") /
|
|
1271
1281
|
intervals).round().astype(int)
|
|
1272
|
-
df["xxxyyyxxx"] = df["
|
|
1282
|
+
df["xxxyyyxxx"] = df["datetime"].map(
|
|
1273
1283
|
lambda x: (x.weekday//mult))*mult
|
|
1274
1284
|
|
|
1275
1285
|
counts = df.groupby([id_col, "xxxyyyxxx"])[
|
|
@@ -1289,27 +1299,27 @@ class Summary(pd.DataFrame):
|
|
|
1289
1299
|
case "hour":
|
|
1290
1300
|
expected = (pd.Timedelta(1, "hour") /
|
|
1291
1301
|
intervals).round().astype(int)
|
|
1292
|
-
df["xxxyyyxxx"] = df["
|
|
1302
|
+
df["xxxyyyxxx"] = df["datetime"].dt.floor("h")
|
|
1293
1303
|
case "day":
|
|
1294
1304
|
expected = (pd.Timedelta(1, "day") /
|
|
1295
1305
|
intervals).round().astype(int)
|
|
1296
|
-
df["xxxyyyxxx"] = df["
|
|
1306
|
+
df["xxxyyyxxx"] = df["datetime"].dt.floor("d")
|
|
1297
1307
|
case "minute":
|
|
1298
1308
|
expected = (pd.Timedelta(1, "minute") /
|
|
1299
1309
|
intervals).round().astype(int)
|
|
1300
|
-
df["xxxyyyxxx"] = df["
|
|
1310
|
+
df["xxxyyyxxx"] = df["datetime"].dt.floor("min")
|
|
1301
1311
|
case "second":
|
|
1302
1312
|
expected = (pd.Timedelta(1, "second") /
|
|
1303
1313
|
intervals).round().astype(int)
|
|
1304
|
-
df["xxxyyyxxx"] = df["
|
|
1314
|
+
df["xxxyyyxxx"] = df["datetime"].dt.floor("s")
|
|
1305
1315
|
case "week":
|
|
1306
1316
|
expected = (pd.Timedelta(1, "W") /
|
|
1307
1317
|
intervals).round().astype(int)
|
|
1308
|
-
df["xxxyyyxxx"] = df["
|
|
1318
|
+
df["xxxyyyxxx"] = df["datetime"].dt.floor("w")
|
|
1309
1319
|
case "weekday":
|
|
1310
1320
|
expected = (pd.Timedelta(1, "day") /
|
|
1311
1321
|
intervals).round().astype(int)
|
|
1312
|
-
df["xxxyyyxxx"] = df["
|
|
1322
|
+
df["xxxyyyxxx"] = df["datetime"].map(
|
|
1313
1323
|
lambda x: (x.weekday()))
|
|
1314
1324
|
if len(freq.split(" ")) == 2:
|
|
1315
1325
|
mult = float(freq.split(" ")[0])
|
|
@@ -1317,32 +1327,32 @@ class Summary(pd.DataFrame):
|
|
|
1317
1327
|
case "hour":
|
|
1318
1328
|
expected = (pd.Timedelta(mult, "hour") /
|
|
1319
1329
|
intervals).round().astype(int)
|
|
1320
|
-
df["xxxyyyxxx"] = df["
|
|
1330
|
+
df["xxxyyyxxx"] = df["datetime"].dt.floor(
|
|
1321
1331
|
f"{mult}h")
|
|
1322
1332
|
case "day":
|
|
1323
1333
|
expected = (pd.Timedelta(mult, "day") /
|
|
1324
1334
|
intervals).round().astype(int)
|
|
1325
|
-
df["xxxyyyxxx"] = df["
|
|
1335
|
+
df["xxxyyyxxx"] = df["datetime"].dt.floor(
|
|
1326
1336
|
f"{mult}d")
|
|
1327
1337
|
case "minute":
|
|
1328
1338
|
expected = (pd.Timedelta(mult, "minute") /
|
|
1329
1339
|
intervals).round().astype(int)
|
|
1330
|
-
df["xxxyyyxxx"] = df["
|
|
1340
|
+
df["xxxyyyxxx"] = df["datetime"].dt.floor(
|
|
1331
1341
|
f"{mult}m")
|
|
1332
1342
|
case "second":
|
|
1333
1343
|
expected = (pd.Timedelta(mult, "second") /
|
|
1334
1344
|
intervals).round().astype(int)
|
|
1335
|
-
df["xxxyyyxxx"] = df["
|
|
1345
|
+
df["xxxyyyxxx"] = df["datetime"].dt.floor(
|
|
1336
1346
|
f"{mult}s")
|
|
1337
1347
|
case "week":
|
|
1338
1348
|
expected = (pd.Timedelta(mult, "W") /
|
|
1339
1349
|
intervals).round().astype(int)
|
|
1340
|
-
df["xxxyyyxxx"] = df["
|
|
1350
|
+
df["xxxyyyxxx"] = df["datetime"].dt.floor(
|
|
1341
1351
|
f"{mult}w")
|
|
1342
1352
|
case "weekday":
|
|
1343
1353
|
expected = (pd.Timedelta(mult, "day") /
|
|
1344
1354
|
intervals).round().astype(int)
|
|
1345
|
-
df["xxxyyyxxx"] = df["
|
|
1355
|
+
df["xxxyyyxxx"] = df["datetime"].map(
|
|
1346
1356
|
lambda x: (x.weekday//mult))*mult
|
|
1347
1357
|
|
|
1348
1358
|
counts = df.groupby([id_col, "xxxyyyxxx"])[
|
|
@@ -1360,36 +1370,36 @@ class Summary(pd.DataFrame):
|
|
|
1360
1370
|
match frequency:
|
|
1361
1371
|
case "hour":
|
|
1362
1372
|
if flooring_timestamp:
|
|
1363
|
-
df[frequency] = df["
|
|
1373
|
+
df[frequency] = df["datetime"].dt.floor("h")
|
|
1364
1374
|
else:
|
|
1365
|
-
df[frequency] = df["
|
|
1375
|
+
df[frequency] = df["datetime"].map(
|
|
1366
1376
|
lambda x: (x.hour))
|
|
1367
1377
|
case "day":
|
|
1368
1378
|
if flooring_timestamp:
|
|
1369
|
-
df[frequency] = df["
|
|
1379
|
+
df[frequency] = df["datetime"].dt.floor("d")
|
|
1370
1380
|
else:
|
|
1371
|
-
df[frequency] = df["
|
|
1381
|
+
df[frequency] = df["datetime"].map(
|
|
1372
1382
|
lambda x: (x.day))
|
|
1373
1383
|
case "minute":
|
|
1374
1384
|
if flooring_timestamp:
|
|
1375
|
-
df[frequency] = df["
|
|
1385
|
+
df[frequency] = df["datetime"].dt.floor("min")
|
|
1376
1386
|
else:
|
|
1377
|
-
df[frequency] = df["
|
|
1387
|
+
df[frequency] = df["datetime"].map(
|
|
1378
1388
|
lambda x: (x.minute))
|
|
1379
1389
|
case "second":
|
|
1380
1390
|
if flooring_timestamp:
|
|
1381
|
-
df[frequency] = df["
|
|
1391
|
+
df[frequency] = df["datetime"].dt.floor("s")
|
|
1382
1392
|
else:
|
|
1383
|
-
df[frequency] = df["
|
|
1393
|
+
df[frequency] = df["datetime"].map(
|
|
1384
1394
|
lambda x: (x.second))
|
|
1385
1395
|
case "week":
|
|
1386
1396
|
if flooring_timestamp:
|
|
1387
|
-
df[frequency] = df["
|
|
1397
|
+
df[frequency] = df["datetime"].dt.floor("w")
|
|
1388
1398
|
else:
|
|
1389
|
-
df[frequency] = df["
|
|
1399
|
+
df[frequency] = df["datetime"].map(
|
|
1390
1400
|
lambda x: (x.week))
|
|
1391
1401
|
case "weekday":
|
|
1392
|
-
df[frequency] = df["
|
|
1402
|
+
df[frequency] = df["datetime"].map(
|
|
1393
1403
|
lambda x: (x.weekday()))
|
|
1394
1404
|
|
|
1395
1405
|
if len(frequency.split(" ")) == 2:
|
|
@@ -1397,40 +1407,40 @@ class Summary(pd.DataFrame):
|
|
|
1397
1407
|
match frequency.split(" ")[1]:
|
|
1398
1408
|
case "hour":
|
|
1399
1409
|
if flooring_timestamp:
|
|
1400
|
-
df[frequency] = df["
|
|
1410
|
+
df[frequency] = df["datetime"].dt.floor(f"{mult}h")
|
|
1401
1411
|
else:
|
|
1402
|
-
df[frequency] = df["
|
|
1412
|
+
df[frequency] = df["datetime"].map(
|
|
1403
1413
|
lambda x: (x.hour//mult))*mult
|
|
1404
1414
|
case "day":
|
|
1405
1415
|
if flooring_timestamp:
|
|
1406
|
-
df[frequency] = df["
|
|
1416
|
+
df[frequency] = df["datetime"].dt.floor(
|
|
1407
1417
|
f"{mult}d")
|
|
1408
1418
|
else:
|
|
1409
|
-
df[frequency] = df["
|
|
1419
|
+
df[frequency] = df["datetime"].map(
|
|
1410
1420
|
lambda x: (x.day//mult))*mult
|
|
1411
1421
|
case "minute":
|
|
1412
1422
|
if flooring_timestamp:
|
|
1413
|
-
df[frequency] = df["
|
|
1423
|
+
df[frequency] = df["datetime"].dt.floor(
|
|
1414
1424
|
f"{mult}min")
|
|
1415
1425
|
else:
|
|
1416
|
-
df[frequency] = df["
|
|
1426
|
+
df[frequency] = df["datetime"].map(
|
|
1417
1427
|
lambda x: (x.minute//mult))*mult
|
|
1418
1428
|
case "second":
|
|
1419
1429
|
if flooring_timestamp:
|
|
1420
|
-
df[frequency] = df["
|
|
1430
|
+
df[frequency] = df["datetime"].dt.floor(
|
|
1421
1431
|
f"{mult}s")
|
|
1422
1432
|
else:
|
|
1423
|
-
df[frequency] = df["
|
|
1433
|
+
df[frequency] = df["datetime"].map(
|
|
1424
1434
|
lambda x: (x.second//mult))*mult
|
|
1425
1435
|
case "week":
|
|
1426
1436
|
if flooring_timestamp:
|
|
1427
|
-
df[frequency] = df["
|
|
1437
|
+
df[frequency] = df["datetime"].dt.floor(
|
|
1428
1438
|
f"{mult}w")
|
|
1429
1439
|
else:
|
|
1430
|
-
df[frequency] = df["
|
|
1440
|
+
df[frequency] = df["datetime"].map(
|
|
1431
1441
|
lambda x: (x.week//mult))*mult
|
|
1432
1442
|
case "weekday":
|
|
1433
|
-
df[frequency] = df["
|
|
1443
|
+
df[frequency] = df["datetime"].map(
|
|
1434
1444
|
lambda x: (x.weekday//mult))*mult
|
|
1435
1445
|
|
|
1436
1446
|
if isinstance(frequency, list):
|
|
@@ -1439,36 +1449,36 @@ class Summary(pd.DataFrame):
|
|
|
1439
1449
|
match freq:
|
|
1440
1450
|
case "hour":
|
|
1441
1451
|
if flooring_timestamp:
|
|
1442
|
-
df[freq] = df["
|
|
1452
|
+
df[freq] = df["datetime"].dt.floor("h")
|
|
1443
1453
|
else:
|
|
1444
|
-
df[freq] = df["
|
|
1454
|
+
df[freq] = df["datetime"].map(
|
|
1445
1455
|
lambda x: (x.hour))
|
|
1446
1456
|
case "day":
|
|
1447
1457
|
if flooring_timestamp:
|
|
1448
|
-
df[freq] = df["
|
|
1458
|
+
df[freq] = df["datetime"].dt.floor("d")
|
|
1449
1459
|
else:
|
|
1450
|
-
df[freq] = df["
|
|
1460
|
+
df[freq] = df["datetime"].map(
|
|
1451
1461
|
lambda x: (x.day))
|
|
1452
1462
|
case "minute":
|
|
1453
1463
|
if flooring_timestamp:
|
|
1454
|
-
df[freq] = df["
|
|
1464
|
+
df[freq] = df["datetime"].dt.floor("min")
|
|
1455
1465
|
else:
|
|
1456
|
-
df[freq] = df["
|
|
1466
|
+
df[freq] = df["datetime"].map(
|
|
1457
1467
|
lambda x: (x.minute))
|
|
1458
1468
|
case "second":
|
|
1459
1469
|
if flooring_timestamp:
|
|
1460
|
-
df[freq] = df["
|
|
1470
|
+
df[freq] = df["datetime"].dt.floor("s")
|
|
1461
1471
|
else:
|
|
1462
|
-
df[freq] = df["
|
|
1472
|
+
df[freq] = df["datetime"].map(
|
|
1463
1473
|
lambda x: (x.second))
|
|
1464
1474
|
case "week":
|
|
1465
1475
|
if flooring_timestamp:
|
|
1466
|
-
df[freq] = df["
|
|
1476
|
+
df[freq] = df["datetime"].dt.floor("w")
|
|
1467
1477
|
else:
|
|
1468
|
-
df[freq] = df["
|
|
1478
|
+
df[freq] = df["datetime"].map(
|
|
1469
1479
|
lambda x: (x.week))
|
|
1470
1480
|
case "weekday":
|
|
1471
|
-
df[freq] = df["
|
|
1481
|
+
df[freq] = df["datetime"].map(
|
|
1472
1482
|
lambda x: (x.weekday()))
|
|
1473
1483
|
|
|
1474
1484
|
if len(freq.split(" ")) == 2:
|
|
@@ -1476,40 +1486,40 @@ class Summary(pd.DataFrame):
|
|
|
1476
1486
|
match freq.split(" ")[1]:
|
|
1477
1487
|
case "hour":
|
|
1478
1488
|
if flooring_timestamp:
|
|
1479
|
-
df[freq] = df["
|
|
1489
|
+
df[freq] = df["datetime"].dt.floor(f"{mult}h")
|
|
1480
1490
|
else:
|
|
1481
|
-
df[freq] = df["
|
|
1491
|
+
df[freq] = df["datetime"].map(
|
|
1482
1492
|
lambda x: (x.hour//mult))*mult
|
|
1483
1493
|
case "day":
|
|
1484
1494
|
if flooring_timestamp:
|
|
1485
|
-
df[freq] = df["
|
|
1495
|
+
df[freq] = df["datetime"].dt.floor(
|
|
1486
1496
|
f"{mult}d")
|
|
1487
1497
|
else:
|
|
1488
|
-
df[freq] = df["
|
|
1498
|
+
df[freq] = df["datetime"].map(
|
|
1489
1499
|
lambda x: (x.day//mult))*mult
|
|
1490
1500
|
case "minute":
|
|
1491
1501
|
if flooring_timestamp:
|
|
1492
|
-
df[freq] = df["
|
|
1502
|
+
df[freq] = df["datetime"].dt.floor(
|
|
1493
1503
|
f"{mult}min")
|
|
1494
1504
|
else:
|
|
1495
|
-
df[freq] = df["
|
|
1505
|
+
df[freq] = df["datetime"].map(
|
|
1496
1506
|
lambda x: (x.minute//mult))*mult
|
|
1497
1507
|
case "second":
|
|
1498
1508
|
if flooring_timestamp:
|
|
1499
|
-
df[freq] = df["
|
|
1509
|
+
df[freq] = df["datetime"].dt.floor(
|
|
1500
1510
|
f"{mult}s")
|
|
1501
1511
|
else:
|
|
1502
|
-
df[freq] = df["
|
|
1512
|
+
df[freq] = df["datetime"].map(
|
|
1503
1513
|
lambda x: (x.second//mult))*mult
|
|
1504
1514
|
case "week":
|
|
1505
1515
|
if flooring_timestamp:
|
|
1506
|
-
df[freq] = df["
|
|
1516
|
+
df[freq] = df["datetime"].dt.floor(
|
|
1507
1517
|
f"{mult}w")
|
|
1508
1518
|
else:
|
|
1509
|
-
df[freq] = df["
|
|
1519
|
+
df[freq] = df["datetime"].map(
|
|
1510
1520
|
lambda x: (x.week//mult))*mult
|
|
1511
1521
|
case "weekday":
|
|
1512
|
-
df[freq] = df["
|
|
1522
|
+
df[freq] = df["datetime"].map(
|
|
1513
1523
|
lambda x: (x.weekday//mult))*mult
|
|
1514
1524
|
|
|
1515
1525
|
if isinstance(frequency, str):
|
|
@@ -308,6 +308,14 @@ def to_datetime(x):
|
|
|
308
308
|
':')[0]), int(x.split('T')[1].split(':')[1]), int(x.split('T')[1].split(':')[2][:-1])
|
|
309
309
|
return dt.datetime(year, month, day, hour, minute, second)
|
|
310
310
|
|
|
311
|
+
|
|
312
|
+
def to_datetime_lcm(x):
|
|
313
|
+
year, month, day = int(x.split('T')[0].split(
|
|
314
|
+
'-')[0]), int(x.split('T')[0].split('-')[1]), int(x.split('T')[0].split('-')[2])
|
|
315
|
+
hour, minute, second = int(x.split('T')[1].split(
|
|
316
|
+
':')[0]), int(x.split('T')[1].split(':')[1]), int(x.split('T')[1].split(':')[2].split(".")[0])
|
|
317
|
+
return dt.datetime(year, month, day, hour, minute, second)
|
|
318
|
+
|
|
311
319
|
def to_datetime_polar(x):
|
|
312
320
|
year, month, day = int(x.split('T')[0].split(
|
|
313
321
|
'-')[0]), int(x.split('T')[0].split('-')[1]), int(x.split('T')[0].split('-')[2])
|
|
@@ -844,9 +852,8 @@ def lascar_processing(directory, file, interpolation=1,interval="30 seconds", in
|
|
|
844
852
|
|
|
845
853
|
def lcm_processing(directory, file, interpolation=1, interval="300 seconds", interpolate_data=True, timezone_shift=dt.timedelta(hours=0)):
|
|
846
854
|
numeric = ["PM2.5", "PM10", "CO2", "NO2", "Temperature", "Humidity"]
|
|
847
|
-
dtformat = '%Y-%m-%dT%H:%M:%S'
|
|
848
855
|
df = pd.read_csv(directory+file)
|
|
849
|
-
df['timestamp'] = df['timestamp'].map(
|
|
856
|
+
df['timestamp'] = df['timestamp'].map(to_datetime_lcm)
|
|
850
857
|
df.set_index('timestamp', inplace=True)
|
|
851
858
|
if interpolate_data:
|
|
852
859
|
df = interpolate(df, 300, interpolation, pd.Timedelta(
|
|
@@ -286,8 +286,8 @@ AGGREGATES = {
|
|
|
286
286
|
|
|
287
287
|
def _default_x(data: pd.DataFrame) -> str:
|
|
288
288
|
"""Return ``time`` when available, otherwise the first column."""
|
|
289
|
-
if "
|
|
290
|
-
return "
|
|
289
|
+
if "datetime" in data.columns:
|
|
290
|
+
return "datetime"
|
|
291
291
|
datetime_columns = [
|
|
292
292
|
column
|
|
293
293
|
for column in data.columns
|
|
@@ -422,7 +422,7 @@ def _parse_datetime_filter(value):
|
|
|
422
422
|
if match:
|
|
423
423
|
return "date", date(*(int(part) for part in match.groups()))
|
|
424
424
|
if re.fullmatch(r"\d{1,2}:\d{2}(?::\d{2}(?:\.\d{1,6})?)?", value):
|
|
425
|
-
return "
|
|
425
|
+
return "datetime", time.fromisoformat(value)
|
|
426
426
|
match = re.fullmatch(
|
|
427
427
|
date_pattern + r"[ T](\d{1,2}):(\d{2})(?::(\d{2})(?:\.(\d{1,6}))?)?", value)
|
|
428
428
|
if match:
|
|
@@ -464,14 +464,14 @@ def _apply_filters(data, subset_filters, datetime_start=None, datetime_end=None)
|
|
|
464
464
|
if start_kind in ("date", "datetime"):
|
|
465
465
|
kwargs["date_start"] = datetime.combine(
|
|
466
466
|
start, time.min) if start_kind == "date" else start
|
|
467
|
-
elif start_kind == "
|
|
467
|
+
elif start_kind == "datetime":
|
|
468
468
|
kwargs["time_start"] = start
|
|
469
469
|
if end_kind in ("date", "datetime"):
|
|
470
470
|
# dtfilter uses an exclusive upper bound. A date-only end bound
|
|
471
471
|
# therefore means the end of that calendar day, not its midnight.
|
|
472
472
|
kwargs["date_end"] = datetime.combine(
|
|
473
473
|
end + timedelta(days=1), time.min) if end_kind == "date" else end
|
|
474
|
-
elif end_kind == "
|
|
474
|
+
elif end_kind == "datetime":
|
|
475
475
|
kwargs["time_end"] = end
|
|
476
476
|
if kwargs:
|
|
477
477
|
filtered = filtered.dtfilter(**kwargs)
|
|
@@ -2110,7 +2110,7 @@ def create_summary_app(
|
|
|
2110
2110
|
values = generated.set_index("index")[component]
|
|
2111
2111
|
current[component] = values.reindex(current.index)
|
|
2112
2112
|
else:
|
|
2113
|
-
valid = current["
|
|
2113
|
+
valid = current["datetime"].notna().to_numpy()
|
|
2114
2114
|
current[component] = pd.NA
|
|
2115
2115
|
if len(generated) == int(valid.sum()):
|
|
2116
2116
|
current.loc[valid,
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|