Added functions to compare policies
This commit is contained in:
@@ -10,61 +10,113 @@ Determining 2 thresholds for battery charging and discharging. Charging when the
|
||||
Training data: 01-01-2020 - 31-12-2022
|
||||
Test data: 01-01-2023 - 12-12-2023
|
||||
|
||||
| | Charge treshold | Discharge treshold | Charging Cost | Discharging Profit | Total Profit | Charge cycles | Mean charging price | Mean discharging price |
|
||||
|---:|------------------:|---------------------:|----------------:|---------------------:|---------------:|----------------:|----------------------:|-------------------------:|
|
||||
| 0 | 150 | 100 | 184072 | 1.03303e+06 | 848962 | 1884.62 | 32.4889 | 332.002 |
|
||||
| 0 | 150 | 0 | 184072 | 1.03303e+06 | 848962 | 1884.62 | 32.4889 | 332.002 |
|
||||
| 0 | 150 | -100 | 184072 | 1.03303e+06 | 848962 | 1884.62 | 32.4889 | 332.002 |
|
||||
| 0 | 150 | -50 | 184072 | 1.03303e+06 | 848962 | 1884.62 | 32.4889 | 332.002 |
|
||||
| 0 | 150 | 50 | 184072 | 1.03303e+06 | 848962 | 1884.62 | 32.4889 | 332.002 |
|
||||
| 0 | 150 | 150 | 182152 | 1.02598e+06 | 843824 | 1860.12 | 32.4889 | 333.447 |
|
||||
| 0 | 200 | 150 | 248326 | 1.0773e+06 | 828976 | 1695.5 | 42.9038 | 367.058 |
|
||||
| 0 | 200 | 100 | 248326 | 1.0773e+06 | 828976 | 1695.5 | 42.9038 | 367.058 |
|
||||
| 0 | 200 | 50 | 248326 | 1.0773e+06 | 828976 | 1695.5 | 42.9038 | 367.058 |
|
||||
| 0 | 200 | 0 | 248326 | 1.0773e+06 | 828976 | 1695.5 | 42.9038 | 367.058 |
|
||||
| 0 | 200 | -50 | 248326 | 1.0773e+06 | 828976 | 1695.5 | 42.9038 | 367.058 |
|
||||
| 0 | 200 | -100 | 248326 | 1.0773e+06 | 828976 | 1695.5 | 42.9038 | 367.058 |
|
||||
| 0 | 200 | 200 | 247560 | 1.07529e+06 | 827727 | 1690 | 42.9038 | 367.44 |
|
||||
| 0 | 150 | 200 | 151145 | 937599 | 786454 | 1514.88 | 32.4889 | 367.44 |
|
||||
| 0 | 100 | -100 | 85591.8 | 865530 | 779938 | 1978.12 | 19.9739 | 283.851 |
|
||||
| 0 | 100 | 50 | 85591.8 | 865530 | 779938 | 1978.12 | 19.9739 | 283.851 |
|
||||
| 0 | 100 | 0 | 85591.8 | 865530 | 779938 | 1978.12 | 19.9739 | 283.851 |
|
||||
| 0 | 100 | -50 | 85591.8 | 865530 | 779938 | 1978.12 | 19.9739 | 283.851 |
|
||||
| 0 | 100 | 100 | 84872.7 | 864043 | 779171 | 1966.62 | 19.9739 | 284.61 |
|
||||
| 0 | 100 | 150 | 63807.1 | 802437 | 738630 | 1502.5 | 19.9739 | 333.447 |
|
||||
| 0 | 50 | 50 | -35789.2 | 689455 | 725244 | 2831 | -9.65396 | 204.943 |
|
||||
| 0 | 50 | -100 | -35776.3 | 688933 | 724710 | 2833.88 | -9.65396 | 204.79 |
|
||||
| 0 | 50 | 0 | -35776.3 | 688933 | 724710 | 2833.88 | -9.65396 | 204.79 |
|
||||
| 0 | 50 | -50 | -35776.3 | 688933 | 724710 | 2833.88 | -9.65396 | 204.79 |
|
||||
| 0 | 100 | 200 | 49469.3 | 721380 | 671911 | 1196.12 | 19.9739 | 367.44 |
|
||||
| 0 | 50 | 100 | -46110.5 | 592694 | 638805 | 1417.5 | -9.65396 | 284.61 |
|
||||
| 0 | 50 | 150 | -45858.6 | 531472 | 577330 | 1007.5 | -9.65396 | 333.447 |
|
||||
| 0 | 50 | 200 | -43738 | 473478 | 517216 | 779.25 | -9.65396 | 367.44 |
|
||||
| 0 | 0 | 100 | -97804.3 | 341072 | 438876 | 761.5 | -73.2011 | 284.61 |
|
||||
| 0 | 0 | 50 | -121468 | 314671 | 436139 | 993.625 | -73.2011 | 204.943 |
|
||||
| 0 | 0 | 150 | -85919 | 341046 | 426964 | 635.75 | -73.2011 | 333.447 |
|
||||
| 0 | 0 | 200 | -75822.2 | 328188 | 404010 | 541.25 | -73.2011 | 367.44 |
|
||||
| 0 | 0 | 0 | -135954 | 259915 | 395869 | 1110.12 | -73.2011 | 146.436 |
|
||||
| 0 | 0 | -100 | -136936 | 251758 | 388694 | 1117.5 | -73.2011 | 145.226 |
|
||||
| 0 | 0 | -50 | -136936 | 251758 | 388694 | 1117.5 | -73.2011 | 145.226 |
|
||||
| 0 | -50 | 150 | -97889.1 | 219525 | 317414 | 409.312 | -127.845 | 333.447 |
|
||||
| 0 | -50 | 100 | -108274 | 208273 | 316548 | 458.312 | -127.845 | 284.61 |
|
||||
| 0 | -50 | 200 | -87698.7 | 223235 | 310933 | 363.625 | -127.845 | 367.44 |
|
||||
| 0 | -50 | 50 | -124664 | 184027 | 308691 | 525.688 | -127.845 | 204.943 |
|
||||
| 0 | -50 | 0 | -131679 | 158118 | 289797 | 551.188 | -127.845 | 146.436 |
|
||||
| 0 | -50 | -50 | -138246 | 126218 | 264464 | 576.5 | -127.845 | 136.356 |
|
||||
| 0 | -50 | -100 | -138429 | 125059 | 263488 | 577.625 | -127.845 | 136.262 |
|
||||
| 0 | -100 | 200 | -76499.7 | 137174 | 213674 | 219.625 | -179.829 | 367.44 |
|
||||
| 0 | -100 | 150 | -82202.7 | 128215 | 210418 | 237.125 | -179.829 | 333.447 |
|
||||
| 0 | -100 | 100 | -86319.5 | 117325 | 203645 | 250.25 | -179.829 | 284.61 |
|
||||
| 0 | -100 | 50 | -94055.9 | 99443.5 | 193499 | 269.875 | -179.829 | 204.943 |
|
||||
| 0 | -100 | 0 | -95713.7 | 87279.5 | 182993 | 274.625 | -179.829 | 146.436 |
|
||||
| 0 | -100 | -50 | -97722.9 | 71560.6 | 169283 | 280.375 | -179.829 | 136.356 |
|
||||
| 0 | -100 | -100 | -101133 | 45851.2 | 146985 | 289.375 | -179.829 | 130.542 |
|
||||
| | Charge threshold | Discharge threshold | Charging Cost | Discharging Profit | Total Profit | Charge cycles | Mean charging price | Mean discharging price |
|
||||
|---:|-------------------:|----------------------:|----------------:|---------------------:|---------------:|----------------:|----------------------:|-------------------------:|
|
||||
| 0 | 150 | 175 | 165982 | 989322 | 823340 | 1701.62 | 32.4889 | 348.51 |
|
||||
| 0 | 175 | 200 | 190060 | 1.00145e+06 | 811389 | 1594 | 37.0705 | 367.44 |
|
||||
| 0 | 125 | 150 | 132766 | 939145 | 806378 | 1729.88 | 27.7746 | 333.447 |
|
||||
| 0 | 200 | 225 | 219726 | 1.01789e+06 | 798159 | 1493.12 | 42.9038 | 390.49 |
|
||||
| 0 | 150 | 200 | 151145 | 937599 | 786454 | 1514.88 | 32.4889 | 367.44 |
|
||||
| 0 | 125 | 175 | 122067 | 904885 | 782818 | 1584.62 | 27.7746 | 348.51 |
|
||||
| 0 | 175 | 225 | 173050 | 950270 | 777219 | 1415 | 37.0705 | 390.49 |
|
||||
| 0 | 100 | 125 | 69876.4 | 829454 | 759577 | 1662.88 | 19.9739 | 315.1 |
|
||||
| 0 | 150 | 225 | 136563 | 886279 | 749716 | 1339.12 | 32.4889 | 390.49 |
|
||||
| 0 | 125 | 200 | 109873 | 853728 | 743855 | 1402.5 | 27.7746 | 367.44 |
|
||||
| 0 | 100 | 150 | 63807.1 | 802437 | 738630 | 1502.5 | 19.9739 | 333.447 |
|
||||
| 0 | 100 | 175 | 56405.8 | 770173 | 713768 | 1366.75 | 19.9739 | 348.51 |
|
||||
| 0 | 75 | 100 | 14153.7 | 724660 | 710506 | 1684.5 | 11.3023 | 284.61 |
|
||||
| 0 | 125 | 225 | 97524.1 | 804468 | 706944 | 1231.88 | 27.7746 | 390.49 |
|
||||
| 0 | 25 | 50 | -56542.1 | 637628 | 694171 | 2696.12 | -16.9846 | 204.943 |
|
||||
| 0 | 75 | 125 | 8003.32 | 688780 | 680776 | 1407.38 | 11.3023 | 315.1 |
|
||||
| 0 | 100 | 200 | 49469.3 | 721380 | 671911 | 1196.12 | 19.9739 | 367.44 |
|
||||
| 0 | 50 | 75 | -47575.2 | 614964 | 662539 | 1752 | -9.65396 | 254.211 |
|
||||
| 0 | 75 | 150 | 5147.22 | 661439 | 656292 | 1254.62 | 11.3023 | 333.447 |
|
||||
| 0 | 50 | 100 | -46110.5 | 592694 | 638805 | 1417.5 | -9.65396 | 284.61 |
|
||||
| 0 | 100 | 225 | 42046.6 | 677560 | 635514 | 1042.88 | 19.9739 | 390.49 |
|
||||
| 0 | 75 | 175 | 850.49 | 631552 | 630702 | 1129 | 11.3023 | 348.51 |
|
||||
| 0 | 25 | 75 | -63342.8 | 561356 | 624699 | 1637 | -16.9846 | 254.211 |
|
||||
| 0 | 50 | 125 | -46686.3 | 556263 | 602950 | 1150.5 | -9.65396 | 315.1 |
|
||||
| 0 | 25 | 100 | -61448.6 | 537683 | 599132 | 1306.5 | -16.9846 | 284.61 |
|
||||
| 0 | 75 | 200 | -1767.94 | 590094 | 591862 | 981.5 | 11.3023 | 367.44 |
|
||||
| 0 | 50 | 150 | -45858.6 | 531472 | 577330 | 1007.5 | -9.65396 | 333.447 |
|
||||
| 0 | 25 | 125 | -61228.7 | 500861 | 562089 | 1045.62 | -16.9846 | 315.1 |
|
||||
| 0 | 75 | 225 | -3475.71 | 555727 | 559203 | 855.875 | 11.3023 | 390.49 |
|
||||
| 0 | 50 | 175 | -46084.1 | 506348 | 552432 | 900.875 | -9.65396 | 348.51 |
|
||||
| 0 | 25 | 150 | -60177.2 | 476823 | 537000 | 906.75 | -16.9846 | 333.447 |
|
||||
| 0 | 50 | 200 | -43738 | 473478 | 517216 | 779.25 | -9.65396 | 367.44 |
|
||||
| 0 | 25 | 175 | -59466.7 | 453988 | 513455 | 808.25 | -16.9846 | 348.51 |
|
||||
| 0 | 50 | 225 | -40529.8 | 452651 | 493181 | 693.875 | -9.65396 | 390.49 |
|
||||
| 0 | 25 | 200 | -55766.8 | 426055 | 481822 | 699.875 | -16.9846 | 367.44 |
|
||||
| 0 | 25 | 225 | -51953 | 407484 | 459437 | 623.875 | -16.9846 | 390.49 |
|
||||
| 0 | 0 | 75 | -107853 | 332344 | 440197 | 851.375 | -73.2011 | 254.211 |
|
||||
| 0 | 0 | 100 | -97804.3 | 341072 | 438876 | 761.5 | -73.2011 | 284.61 |
|
||||
| 0 | 0 | 50 | -121468 | 314671 | 436139 | 993.625 | -73.2011 | 204.943 |
|
||||
| 0 | 0 | 125 | -91087.2 | 342646 | 433734 | 686.125 | -73.2011 | 315.1 |
|
||||
| 0 | 0 | 25 | -126590 | 305984 | 432574 | 1041.75 | -73.2011 | 193.87 |
|
||||
| 0 | 0 | 150 | -85919 | 341046 | 426964 | 635.75 | -73.2011 | 333.447 |
|
||||
| 0 | 0 | 175 | -82378.2 | 338310 | 420688 | 600.625 | -73.2011 | 348.51 |
|
||||
| 0 | 0 | 200 | -75822.2 | 328188 | 404010 | 541.25 | -73.2011 | 367.44 |
|
||||
| 0 | 0 | 225 | -69488.7 | 320776 | 390265 | 494.75 | -73.2011 | 390.49 |
|
||||
| 0 | -25 | 125 | -102495 | 269615 | 372110 | 534.062 | -105.73 | 315.1 |
|
||||
| 0 | -25 | 100 | -108934 | 262527 | 371462 | 574.938 | -105.73 | 284.61 |
|
||||
| 0 | -25 | 75 | -118553 | 252453 | 371006 | 626.062 | -105.73 | 254.211 |
|
||||
| 0 | -25 | 150 | -97080 | 271209 | 368289 | 503.438 | -105.73 | 333.447 |
|
||||
| 0 | -25 | 50 | -129918 | 236112 | 366030 | 683.562 | -105.73 | 204.943 |
|
||||
| 0 | -25 | 175 | -92889.5 | 272520 | 365409 | 480.438 | -105.73 | 348.51 |
|
||||
| 0 | -25 | 25 | -132518 | 227910 | 360428 | 695.562 | -105.73 | 193.87 |
|
||||
| 0 | -25 | 200 | -85482.7 | 268638 | 354120 | 438.5 | -105.73 | 367.44 |
|
||||
| 0 | -25 | 225 | -79253.2 | 264052 | 343305 | 403.75 | -105.73 | 390.49 |
|
||||
| 0 | -25 | 0 | -139125 | 199831 | 338956 | 724.312 | -105.73 | 146.436 |
|
||||
| 0 | -50 | 125 | -102665 | 216740 | 319405 | 431.562 | -127.845 | 315.1 |
|
||||
| 0 | -50 | 175 | -94272.2 | 223434 | 317706 | 393.188 | -127.845 | 348.51 |
|
||||
| 0 | -50 | 150 | -97889.1 | 219525 | 317414 | 409.312 | -127.845 | 333.447 |
|
||||
| 0 | -50 | 100 | -108274 | 208273 | 316548 | 458.312 | -127.845 | 284.61 |
|
||||
| 0 | -50 | 75 | -115707 | 198325 | 314032 | 488.438 | -127.845 | 254.211 |
|
||||
| 0 | -50 | 200 | -87698.7 | 223235 | 310933 | 363.625 | -127.845 | 367.44 |
|
||||
| 0 | -50 | 50 | -124664 | 184027 | 308691 | 525.688 | -127.845 | 204.943 |
|
||||
| 0 | -50 | 25 | -126605 | 177834 | 304440 | 533.062 | -127.845 | 193.87 |
|
||||
| 0 | -50 | 225 | -81706.8 | 221510 | 303217 | 337.75 | -127.845 | 390.49 |
|
||||
| 0 | -50 | 0 | -131679 | 158118 | 289797 | 551.188 | -127.845 | 146.436 |
|
||||
| 0 | -50 | -25 | -135234 | 140945 | 276180 | 565 | -127.845 | 139.469 |
|
||||
| 0 | -75 | 175 | -90764.9 | 184846 | 275611 | 325.812 | -146.153 | 348.51 |
|
||||
| 0 | -75 | 125 | -98076.6 | 176722 | 274799 | 355.062 | -146.153 | 315.1 |
|
||||
| 0 | -75 | 150 | -93979.3 | 179914 | 273893 | 338.188 | -146.153 | 333.447 |
|
||||
| 0 | -75 | 100 | -103131 | 169294 | 272425 | 375.062 | -146.153 | 284.61 |
|
||||
| 0 | -75 | 200 | -85036.8 | 186067 | 271104 | 302.375 | -146.153 | 367.44 |
|
||||
| 0 | -75 | 75 | -109431 | 159779 | 269210 | 395.938 | -146.153 | 254.211 |
|
||||
| 0 | -75 | 225 | -79978.8 | 185752 | 265731 | 282.75 | -146.153 | 390.49 |
|
||||
| 0 | -75 | 50 | -116483 | 147147 | 263630 | 421.062 | -146.153 | 204.943 |
|
||||
| 0 | -75 | 25 | -117886 | 141847 | 259734 | 424.812 | -146.153 | 193.87 |
|
||||
| 0 | -75 | 0 | -120983 | 126071 | 247054 | 435.188 | -146.153 | 146.436 |
|
||||
| 0 | -75 | -25 | -123261 | 111930 | 235190 | 443.625 | -146.153 | 139.469 |
|
||||
| 0 | -75 | -50 | -124708 | 101672 | 226380 | 449.25 | -146.153 | 136.356 |
|
||||
| 0 | -100 | 200 | -76499.7 | 137174 | 213674 | 219.625 | -179.829 | 367.44 |
|
||||
| 0 | -100 | 175 | -79830.5 | 132966 | 212797 | 230.125 | -179.829 | 348.51 |
|
||||
| 0 | -100 | 225 | -72449.9 | 138631 | 211081 | 207.625 | -179.829 | 390.49 |
|
||||
| 0 | -100 | 150 | -82202.7 | 128215 | 210418 | 237.125 | -179.829 | 333.447 |
|
||||
| 0 | -100 | 125 | -84192.7 | 123976 | 208169 | 243.625 | -179.829 | 315.1 |
|
||||
| 0 | -100 | 100 | -86319.5 | 117325 | 203645 | 250.25 | -179.829 | 284.61 |
|
||||
| 0 | -100 | 75 | -90219.7 | 109153 | 199373 | 259.25 | -179.829 | 254.211 |
|
||||
| 0 | -100 | 50 | -94055.9 | 99443.5 | 193499 | 269.875 | -179.829 | 204.943 |
|
||||
| 0 | -100 | 25 | -94464.1 | 96073.2 | 190537 | 270.875 | -179.829 | 193.87 |
|
||||
| 0 | -100 | 0 | -95713.7 | 87279.5 | 182993 | 274.625 | -179.829 | 146.436 |
|
||||
| 0 | -100 | -25 | -97020.3 | 78656.5 | 175677 | 278.25 | -179.829 | 139.469 |
|
||||
| 0 | -100 | -50 | -97722.9 | 71560.6 | 169283 | 280.375 | -179.829 | 136.356 |
|
||||
| 0 | -100 | -75 | -98604.6 | 63373.8 | 161978 | 282.625 | -179.829 | 134.012 |
|
||||
|
||||
## Optimal policy
|
||||
Charge threshold: 150 €/MWh \
|
||||
Discharge threshold: 100 €/MWh
|
||||
Discharge threshold: 175 €/MWh
|
||||
|
||||
Profit on test data: € 169846.84 \
|
||||
Charge cycles: 1403
|
||||
Profit on test data: € 359548 \
|
||||
Charge cycles: 855.938
|
||||
|
||||
|
||||
# Smarter Policy using predicted NRV
|
||||
Test data: 01-01-2023 until 08-10–2023
|
||||
|
||||
| Policy | Threshold Step Size (€) | Total Profit (€) | Charge Cycles |
|
||||
|--------|---------------------|--------------|---------------|
|
||||
| Baseline (charge: 150, discharge: 175) | 25 | 251202.59 | 725 |
|
||||
| Policy using predicted NRV | 50 | 325362.81 | 856 |
|
||||
| Policy using predicted NRV | 25 | 334058.65 | 862 |
|
||||
@@ -207,4 +207,11 @@ class NrvDataset(Dataset):
|
||||
return torch.stack(features), torch.stack(targets)
|
||||
|
||||
def get_idx_for_date(self, date: datetime.date):
|
||||
return self.datetime[self.datetime.dt.date == date].index[0]
|
||||
# check if the date is in the valid indices
|
||||
if date not in self.datetime.dt.date.unique():
|
||||
raise ValueError(f"Date {date} not in dataset.")
|
||||
|
||||
idx = self.datetime[self.datetime.dt.date == date].index[0]
|
||||
|
||||
valid_idx = self.valid_indices.index(idx)
|
||||
return valid_idx
|
||||
File diff suppressed because one or more lines are too long
@@ -57,7 +57,8 @@ class Battery:
|
||||
self.charge_cycles = 0
|
||||
|
||||
class BaselinePolicy():
|
||||
def __init__(self, battery: Battery):
|
||||
def __init__(self, battery: Battery, data_path: str = ""):
|
||||
self.data_path = data_path
|
||||
self.battery = battery
|
||||
self.train_data = self.load_imbalance_prices(train=True)
|
||||
self.test_data = self.load_imbalance_prices(train=False)
|
||||
@@ -67,7 +68,7 @@ class BaselinePolicy():
|
||||
print(f"Test range: {self.test_data.iloc[0]['DateTime'].strftime('%d-%m-%Y')} - {self.test_data.iloc[-1]['DateTime'].strftime('%d-%m-%Y')}")
|
||||
|
||||
def load_imbalance_prices(self, train: bool = True):
|
||||
imbalance_prices = pd.read_csv('data/imbalance_prices.csv', parse_dates=True, sep=";")
|
||||
imbalance_prices = pd.read_csv(self.data_path + 'data/imbalance_prices.csv', parse_dates=True, sep=";")
|
||||
imbalance_prices = imbalance_prices[['DateTime', 'Positive imbalance price']]
|
||||
imbalance_prices['DateTime'] = pd.to_datetime(imbalance_prices['DateTime'], utc=True)
|
||||
if train:
|
||||
@@ -78,15 +79,15 @@ class BaselinePolicy():
|
||||
imbalance_prices = imbalance_prices.sort_values(by=['DateTime'], ascending=True)
|
||||
return imbalance_prices
|
||||
|
||||
def get_train_score(self, charge_treshold, discharge_treshold):
|
||||
return self.get_score(self.train_data, charge_treshold, discharge_treshold)
|
||||
def get_train_score(self, charge_threshold, discharge_threshold):
|
||||
return self.get_score(self.train_data, charge_threshold, discharge_threshold)
|
||||
|
||||
def get_test_score(self, charge_treshold, discharge_treshold):
|
||||
return self.get_score(self.test_data, charge_treshold, discharge_treshold)
|
||||
def get_test_score(self, charge_threshold, discharge_threshold):
|
||||
return self.get_score(self.test_data, charge_threshold, discharge_threshold)
|
||||
|
||||
# if price is below charging treshold (cheap charging) -> charge battery: total_profit -= charge * price
|
||||
# if price is above treshold -> discharge battery: total_profit += discharge * price
|
||||
def get_score(self, df, charge_treshold, discharge_treshold):
|
||||
# if price is below charging threshold (cheap charging) -> charge battery: total_profit -= charge * price
|
||||
# if price is above threshold -> discharge battery: total_profit += discharge * price
|
||||
def get_score(self, df, charge_threshold, discharge_threshold):
|
||||
self.battery.reset()
|
||||
total_charging_cost = 0
|
||||
total_discharging_profit = 0
|
||||
@@ -96,41 +97,141 @@ class BaselinePolicy():
|
||||
number_of_discharges = 0
|
||||
|
||||
for index, row in df.iterrows():
|
||||
if row['Positive imbalance price'] < charge_treshold:
|
||||
if row['Positive imbalance price'] < charge_threshold:
|
||||
total_charging_cost += self.battery.charge() * row['Positive imbalance price']
|
||||
mean_charging_price += row['Positive imbalance price']
|
||||
number_of_charges += 1
|
||||
elif row['Positive imbalance price'] > discharge_treshold:
|
||||
elif row['Positive imbalance price'] > discharge_threshold:
|
||||
total_discharging_profit += self.battery.discharge() * row['Positive imbalance price']
|
||||
mean_discharging_price += row['Positive imbalance price']
|
||||
number_of_discharges += 1
|
||||
|
||||
return total_charging_cost, total_discharging_profit, self.battery.charge_cycles, mean_charging_price / number_of_charges, mean_discharging_price / number_of_discharges
|
||||
|
||||
def treshold_scores(self, charge_tresholds, discharge_tresholds):
|
||||
df = pd.DataFrame(columns=["Charge treshold", "Discharge treshold", "Charging Cost", "Discharging Profit", "Total Profit", "Charge cycles", "Mean charging price", "Mean discharging price"])
|
||||
df_test = pd.DataFrame(columns=["Charge treshold", "Discharge treshold", "Charging Cost", "Discharging Profit", "Total Profit", "Charge cycles", "Mean charging price", "Mean discharging price"])
|
||||
for charge_treshold, discharge_treshold in tqdm(itertools.product(charge_tresholds, discharge_tresholds)):
|
||||
total_charging_cost, total_discharge_profit, charge_cycles, mean_charging_price, mean_discharging_price = self.get_train_score(charge_treshold, discharge_treshold)
|
||||
df = pd.concat([df, pd.DataFrame([[charge_treshold, discharge_treshold, total_charging_cost, total_discharge_profit, total_discharge_profit - total_charging_cost, charge_cycles, mean_charging_price, mean_discharging_price]], columns=["Charge treshold", "Discharge treshold", "Charging Cost", "Discharging Profit", "Total Profit", "Charge cycles", "Mean charging price", "Mean discharging price"])])
|
||||
def threshold_scores(self, charge_thresholds, discharge_thresholds):
|
||||
df = pd.DataFrame(columns=["Charge threshold", "Discharge threshold", "Charging Cost", "Discharging Profit", "Total Profit", "Charge cycles", "Mean charging price", "Mean discharging price"])
|
||||
df_test = pd.DataFrame(columns=["Charge threshold", "Discharge threshold", "Charging Cost", "Discharging Profit", "Total Profit", "Charge cycles", "Mean charging price", "Mean discharging price"])
|
||||
|
||||
total_charging_cost, total_discharge_profit, charge_cycles, mean_charging_price, mean_discharging_price = self.get_test_score(charge_treshold, discharge_treshold)
|
||||
df_test = pd.concat([df_test, pd.DataFrame([[charge_treshold, discharge_treshold, total_charging_cost, total_discharge_profit, total_discharge_profit - total_charging_cost, charge_cycles, mean_charging_price, mean_discharging_price]], columns=["Charge treshold", "Discharge treshold", "Charging Cost", "Discharging Profit", "Total Profit", "Charge cycles", "Mean charging price", "Mean discharging price"])])
|
||||
threshold_pairs = itertools.product(charge_thresholds, discharge_thresholds)
|
||||
threshold_pairs = filter(lambda x: x[0] < x[1], threshold_pairs)
|
||||
|
||||
for charge_threshold, discharge_threshold in tqdm(threshold_pairs):
|
||||
total_charging_cost, total_discharge_profit, charge_cycles, mean_charging_price, mean_discharging_price = self.get_train_score(charge_threshold, discharge_threshold)
|
||||
df = pd.concat([df, pd.DataFrame([[charge_threshold, discharge_threshold, total_charging_cost, total_discharge_profit, total_discharge_profit - total_charging_cost, charge_cycles, mean_charging_price, mean_discharging_price]], columns=["Charge threshold", "Discharge threshold", "Charging Cost", "Discharging Profit", "Total Profit", "Charge cycles", "Mean charging price", "Mean discharging price"])])
|
||||
|
||||
total_charging_cost, total_discharge_profit, charge_cycles, mean_charging_price, mean_discharging_price = self.get_test_score(charge_threshold, discharge_threshold)
|
||||
df_test = pd.concat([df_test, pd.DataFrame([[charge_threshold, discharge_threshold, total_charging_cost, total_discharge_profit, total_discharge_profit - total_charging_cost, charge_cycles, mean_charging_price, mean_discharging_price]], columns=["Charge threshold", "Discharge threshold", "Charging Cost", "Discharging Profit", "Total Profit", "Charge cycles", "Mean charging price", "Mean discharging price"])])
|
||||
|
||||
df = df.sort_values(by=['Total Profit'], ascending=False)
|
||||
|
||||
return df, df_test
|
||||
|
||||
def get_optimal_thresholds(self, imbalance_prices, charge_thresholds, discharge_thresholds, tqdm=True):
|
||||
df = None
|
||||
|
||||
threshold_pairs = itertools.product(charge_thresholds, discharge_thresholds)
|
||||
threshold_pairs = filter(lambda x: x[0] < x[1], threshold_pairs)
|
||||
|
||||
# disable tqdm if necessary
|
||||
if tqdm:
|
||||
threshold_pairs = tqdm(threshold_pairs)
|
||||
|
||||
for charge_threshold, discharge_threshold in threshold_pairs:
|
||||
self.battery.reset()
|
||||
total_charging_cost = 0
|
||||
total_discharging_profit = 0
|
||||
number_of_charges = 0
|
||||
number_of_discharges = 0
|
||||
mean_charging_price = 0
|
||||
mean_discharging_price = 0
|
||||
|
||||
for index, price in enumerate(imbalance_prices):
|
||||
if price < charge_threshold:
|
||||
total_charging_cost += self.battery.charge() * price
|
||||
mean_charging_price += price
|
||||
number_of_charges += 1
|
||||
elif price > discharge_threshold:
|
||||
total_discharging_profit += self.battery.discharge() * price
|
||||
mean_discharging_price += price
|
||||
number_of_discharges += 1
|
||||
|
||||
if number_of_charges == 0:
|
||||
mean_charging_price = 0
|
||||
else:
|
||||
mean_charging_price /= number_of_charges
|
||||
|
||||
if number_of_discharges == 0:
|
||||
mean_discharging_price = 0
|
||||
else:
|
||||
mean_discharging_price /= number_of_discharges
|
||||
|
||||
new_df = pd.DataFrame([[charge_threshold, discharge_threshold, total_charging_cost, total_discharging_profit, total_discharging_profit - total_charging_cost, self.battery.charge_cycles, mean_charging_price, mean_discharging_price]], columns=["Charge threshold", "Discharge threshold", "Charging Cost", "Discharging Profit", "Total Profit", "Charge cycles", "Mean charging price", "Mean discharging price"])
|
||||
if df is None:
|
||||
df = new_df
|
||||
else:
|
||||
df = pd.concat([df, new_df])
|
||||
|
||||
df = df.sort_values(by=['Total Profit'], ascending=False)
|
||||
|
||||
return df
|
||||
|
||||
def simulate(self, imbalance_prices, charge_threshold, discharge_threshold):
|
||||
self.battery.reset()
|
||||
total_charging_cost = 0
|
||||
total_discharging_profit = 0
|
||||
number_of_charges = 0
|
||||
number_of_discharges = 0
|
||||
mean_charging_price = 0
|
||||
mean_discharging_price = 0
|
||||
|
||||
# for each timestep also print what is happening
|
||||
for i, price in enumerate(imbalance_prices):
|
||||
if price < charge_threshold:
|
||||
charge = self.battery.charge()
|
||||
total_charging_cost += charge * price
|
||||
mean_charging_price += price
|
||||
number_of_charges += 1
|
||||
# print(f"{i}: Charging battery with {charge}MWh at {price}€/MWh")
|
||||
|
||||
elif price > discharge_threshold:
|
||||
discharge = self.battery.discharge()
|
||||
total_discharging_profit += discharge * price
|
||||
mean_discharging_price += price
|
||||
number_of_discharges += 1
|
||||
# print(f"{i}: Discharging battery with {discharge}MWh at {price}€/MWh")
|
||||
|
||||
if number_of_charges == 0:
|
||||
mean_charging_price = 0
|
||||
else:
|
||||
mean_charging_price /= number_of_charges
|
||||
|
||||
if number_of_discharges == 0:
|
||||
mean_discharging_price = 0
|
||||
else:
|
||||
mean_discharging_price /= number_of_discharges
|
||||
|
||||
# print(f"Total charging cost: {total_charging_cost}")
|
||||
# print(f"Total discharging profit: {total_discharging_profit}")
|
||||
# print(f"Total profit: {total_discharging_profit - total_charging_cost}")
|
||||
# print(f"Charge cycles: {self.battery.charge_cycles}")
|
||||
# print(f"Mean charging price: {mean_charging_price}")
|
||||
# print(f"Mean discharging price: {mean_discharging_price}")
|
||||
|
||||
return total_discharging_profit - total_charging_cost, self.battery.charge_cycles
|
||||
|
||||
|
||||
|
||||
|
||||
battery = Battery(2, 1)
|
||||
policy = BaselinePolicy(battery)
|
||||
# battery = Battery(2, 1)
|
||||
# policy = BaselinePolicy(battery)
|
||||
|
||||
charge_tresholds = np.arange(-100, 250, 50)
|
||||
discharge_tresholds = np.arange(-100, 250, 50)
|
||||
|
||||
df, df_test = policy.treshold_scores(charge_tresholds, discharge_tresholds)
|
||||
print(df.to_markdown())
|
||||
# charge_thresholds = np.arange(-100, 250, 25)
|
||||
# discharge_thresholds = np.arange(-100, 250, 25)
|
||||
|
||||
print(df_test.to_markdown())
|
||||
# df, df_test = policy.threshold_scores(charge_thresholds, discharge_thresholds)
|
||||
# print(df.to_markdown())
|
||||
|
||||
# print(policy.get_test_score(150, 100))
|
||||
# print(df_test.to_markdown())
|
||||
|
||||
# # print(policy.get_test_score(150, 100))
|
||||
@@ -1,6 +1,6 @@
|
||||
from datetime import datetime
|
||||
import plotly.graph_objects as go
|
||||
import numpy as np
|
||||
import pytz
|
||||
import pandas as pd
|
||||
|
||||
incremental_bids = "../../data/incremental_bids.csv"
|
||||
@@ -66,8 +66,6 @@ class ImbalancePriceCalculator:
|
||||
dec_bids = row["bid_ladder_dec"].values[0]
|
||||
inc_bids = row["bid_ladder_inc"].values[0]
|
||||
|
||||
|
||||
|
||||
# Prepare data for plot
|
||||
x_inc_interpolated = [vol for i in range(len(inc_bids) - 1) for vol in [inc_bids[i][0], inc_bids[i+1][0]]]
|
||||
y_inc_interpolated = [price for cum_vol, price in inc_bids for _ in (0, 1)]
|
||||
@@ -90,6 +88,14 @@ class ImbalancePriceCalculator:
|
||||
|
||||
fig.show()
|
||||
|
||||
def get_imbalance_prices_2023_for_date(self, date, NRV_predictions):
|
||||
imbalance_prices = []
|
||||
for i in range(1, len(NRV_predictions)):
|
||||
datetime = date + pd.Timedelta(hours=i-1)
|
||||
datetime = pytz.utc.localize(datetime)
|
||||
imbalance_prices.append(self.get_imbalance_price_2023(datetime, NRV_predictions[i-1], NRV_predictions[i]))
|
||||
return [x[1] for x in imbalance_prices]
|
||||
|
||||
def get_imbalance_price_2023(self, datetime, NRV_PREV, NRV):
|
||||
MIP = self.get_imbalance_price(datetime, abs(NRV))
|
||||
MDP = self.get_imbalance_price(datetime, -abs(NRV))
|
||||
|
||||
Reference in New Issue
Block a user