%reset
import pandas as pd
import numpy as np
from bs4 import BeautifulSoup as bs
import TOU_pricing
#reload(TOU_pricing)
Assuming we're using deep discharge lead acid batteries like this one on Amazon:
http://www.amazon.com/gp/product/B0044Z8DJW/ref=ox_sc_act_title_1?ie=UTF8&psc=1&smid=A10QFO4IXVZNRN
Residential pricing plansfrom BGE:
inverter_controller_cost = 500. # ballpark
storage_cost_perkWh = 200./1.2 # cost per kilowatt-hour based on link above
cost_per_kWh = .12
cost_per_kWh_red = .08
cost_diff_kWh = cost_per_kWh - cost_per_kWh_red
storage_size_kWh = 6.*1. # storage size in Watt-hours, starting point 6 hours at 1.5 kW
P_max_charge = 12 * 20 / 1000. # maximum charge rate 12 V * 20 A = .24 kW
initial_investment = inverter_controller_cost + storage_cost_perkWh * storage_size_kWh
Need to parse the xml file of the Green Button data.
xml_file = 'raw_data/Inland_Single_Family_Jan_1_2011_to_Jan_1_2012_RetailCustomer_9.xml'
soup = bs(open(xml_file))
# initiate a numpy array to store values
data_array = np.zeros((len(soup.find_all('value')),1))
# In the Green Button schema, the IntervalReading tag designates each reading
# Each IntervalReading has a 'time' element with start and duration children
# 'Value' element is actual hourly usage in Watt-hours
for i, intervalreading in enumerate(soup.find_all('intervalreading')):
data_array[i,0]=intervalreading.value.get_text()
# Convert the array into a Pandas DataFrame for ease of time series use
data_start = '1/1/2011 08:00:00'
demand_data = pd.DataFrame(data_array*.001,columns=['USAGE'],index=pd.date_range(data_start, periods=len(soup.find_all('value')), freq='H'))
#demand_data.to_csv('raw_data/Green_Button_Sample_Inland_SingleFamily.csv')
# Plot
fig = plt.figure(figsize=[12,4])
plot1 = demand_data['USAGE'].resample('d',how=sum).plot(grid='off',linewidth=2)
ylabel('Daily Total Usage (kWh)')
title('Green Button Sample Hourly Data, Resampled to Daily \n "Inland Single Family Residence"')
fig.savefig('plots/Green_Button_Sample_Inland_Single_Family_Daily.png')
fig = plt.figure(figsize=[12,4])
plot1 = demand_data['USAGE'].plot(grid='off',linewidth=0.25)
ylabel('Hourly Usage (kWh)')
<matplotlib.text.Text at 0xa6436d0>
BGE offers three residential pricing plans: R, RL, and EV. R is the basic residential (one electricity price). RL is a TOU option. EV is a more aggressive TOU option for residences that need to charge electric vehicles at night. See References section above.
hourly_state = TOU_pricing.BGE_elec_cost(demand_data)
fig = plt.figure(figsize=[8,4])
plot_start = '20-jun-2011'
plot_end = '20-jun-2011'
plot3 = hourly_state['BGE-EV_cost_perkWh'].ix[plot_start:plot_end].plot(color='green',grid='off',marker='o')
plot1 = hourly_state['BGE-RL_cost_perkWh'].ix[plot_start:plot_end].plot(color='blue',marker='o')
plot2 = hourly_state['BGE-R_cost_perkWh'].ix[plot_start:plot_end].plot(color='red',grid='off',marker='o')
ylabel('Cost of Elec. ($/kWh)')
xlabel('Hour of Day')
title('BGE Residential Pricing Plans, Weekday \n June 1 - September 30')
legend(['EV','RL','R'],loc='upper left')
ylim([0,.2])
#fig.savefig('plots/BGE_Pricing_Summer.png')
(0, 0.2)
fig = plt.figure(figsize=[8,4])
plot_start = '22-nov-2011'
plot_end = '22-nov-2011'
plot3 = hourly_state['BGE-EV_cost_perkWh'].ix[plot_start:plot_end].plot(color='green',grid='off',marker='o')
plot1 = hourly_state['BGE-RL_cost_perkWh'].ix[plot_start:plot_end].plot(color='blue',marker='o')
plot2 = hourly_state['BGE-R_cost_perkWh'].ix[plot_start:plot_end].plot(color='red',grid='off',marker='o')
ylabel('Cost of Elec. ($/kWh)')
xlabel('Hour of Day')
title('BGE Residential Pricing Plans, Weekday \n October 1 - May 31')
legend(['EV','RL','R'],loc='upper left')
ylim([0,.2])
#fig.savefig('plots/BGE_Pricing_Non-Summer.png')
(0, 0.2)
hourly_state['storage_available'] = ones(len(hourly_state['USAGE'])) # kWh
hourly_state['purchase'] = zeros(len(hourly_state['USAGE'])) # kWh
--------------------------------------------------------------------------- NameError Traceback (most recent call last) <ipython-input-46-8b1aa0155d75> in <module>() ----> 1 hourly_state['storage_available'] = ones(len(hourly_state['USAGE'])) # kWh 2 hourly_state['purchase'] = zeros(len(hourly_state['USAGE'])) # kWh 3 NameError: name 'ones' is not defined
for i, value in enumerate(hourly_state['USAGE']):
if hourly_state['USAGE'][i] > hourly_state['storage_available'][i]:
hourly_state['purchase'][i] = hourly_state['USAGE'][i] - hourly_state['storage_available'][i]
#del hourly_state
reload(TOU_pricing)
hourly_state = TOU_pricing.period(demand_data)
hourly_state[40:80]
#demand_data[40:80]
USAGE | BGE-RL | BGE-EV | |
---|---|---|---|
2011-01-03 00:00:00 | 1.090 | offpeak | offpeak |
2011-01-03 01:00:00 | 1.405 | offpeak | offpeak |
2011-01-03 02:00:00 | 1.500 | offpeak | offpeak |
2011-01-03 03:00:00 | 1.404 | offpeak | offpeak |
2011-01-03 04:00:00 | 1.314 | offpeak | offpeak |
2011-01-03 05:00:00 | 1.247 | offpeak | offpeak |
2011-01-03 06:00:00 | 1.089 | offpeak | offpeak |
2011-01-03 07:00:00 | 0.924 | peak | peak |
2011-01-03 08:00:00 | 0.808 | peak | peak |
2011-01-03 09:00:00 | 0.748 | peak | peak |
2011-01-03 10:00:00 | 0.714 | peak | peak |
2011-01-03 11:00:00 | 0.690 | int | offpeak |
2011-01-03 12:00:00 | 0.711 | int | offpeak |
2011-01-03 13:00:00 | 0.829 | int | offpeak |
2011-01-03 14:00:00 | 0.964 | int | offpeak |
2011-01-03 15:00:00 | 0.962 | int | offpeak |
2011-01-03 16:00:00 | 1.050 | int | offpeak |
2011-01-03 17:00:00 | 1.096 | peak | offpeak |
2011-01-03 18:00:00 | 1.111 | peak | offpeak |
2011-01-03 19:00:00 | 1.127 | peak | offpeak |
2011-01-03 20:00:00 | 1.165 | peak | offpeak |
2011-01-03 21:00:00 | 1.055 | offpeak | offpeak |
2011-01-03 22:00:00 | 1.007 | offpeak | offpeak |
2011-01-03 23:00:00 | 0.982 | offpeak | offpeak |
2011-01-04 00:00:00 | 1.057 | offpeak | offpeak |
2011-01-04 01:00:00 | 1.399 | offpeak | offpeak |
2011-01-04 02:00:00 | 1.532 | offpeak | offpeak |
2011-01-04 03:00:00 | 1.444 | offpeak | offpeak |
2011-01-04 04:00:00 | 1.445 | offpeak | offpeak |
2011-01-04 05:00:00 | 1.275 | offpeak | offpeak |
2011-01-04 06:00:00 | 1.040 | offpeak | offpeak |
2011-01-04 07:00:00 | 0.843 | peak | peak |
2011-01-04 08:00:00 | 0.706 | peak | peak |
2011-01-04 09:00:00 | 0.663 | peak | peak |
2011-01-04 10:00:00 | 0.664 | peak | peak |
2011-01-04 11:00:00 | 0.666 | int | offpeak |
2011-01-04 12:00:00 | 0.726 | int | offpeak |
2011-01-04 13:00:00 | 0.871 | int | offpeak |
2011-01-04 14:00:00 | 0.999 | int | offpeak |
2011-01-04 15:00:00 | 1.059 | int | offpeak |
reload(TOU_pricing)
b = TOU_pricing.period(demand_data)
stupid = '2011-01-21'
print b.ix[stupid].index.weekday
b.ix[stupid]
[4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4]
USAGE | BGE-EV | BGE-RL | BGE-R_cost_perkWh | BGE-RL_cost_perkWh | BGE-EV_cost_perkWh | |
---|---|---|---|---|---|---|
2011-01-21 00:00:00 | 0.997 | offpeak | offpeak | 0.08616 | 0.06974 | 0.05209 |
2011-01-21 01:00:00 | 1.261 | offpeak | offpeak | 0.08616 | 0.06974 | 0.05209 |
2011-01-21 02:00:00 | 1.429 | offpeak | offpeak | 0.08616 | 0.06974 | 0.05209 |
2011-01-21 03:00:00 | 1.343 | offpeak | offpeak | 0.08616 | 0.06974 | 0.05209 |
2011-01-21 04:00:00 | 1.300 | offpeak | offpeak | 0.08616 | 0.06974 | 0.05209 |
2011-01-21 05:00:00 | 1.168 | offpeak | offpeak | 0.08616 | 0.06974 | 0.05209 |
2011-01-21 06:00:00 | 0.980 | offpeak | offpeak | 0.08616 | 0.06974 | 0.05209 |
2011-01-21 07:00:00 | 0.784 | peak | peak | 0.08616 | 0.11924 | 0.18266 |
2011-01-21 08:00:00 | 0.669 | peak | peak | 0.08616 | 0.11924 | 0.18266 |
2011-01-21 09:00:00 | 0.626 | peak | peak | 0.08616 | 0.11924 | 0.18266 |
2011-01-21 10:00:00 | 0.628 | peak | peak | 0.08616 | 0.11924 | 0.18266 |
2011-01-21 11:00:00 | 0.626 | offpeak | int | 0.08616 | 0.08468 | 0.05209 |
2011-01-21 12:00:00 | 0.678 | offpeak | int | 0.08616 | 0.08468 | 0.05209 |
2011-01-21 13:00:00 | 0.862 | offpeak | int | 0.08616 | 0.08468 | 0.05209 |
2011-01-21 14:00:00 | 0.993 | offpeak | int | 0.08616 | 0.08468 | 0.05209 |
2011-01-21 15:00:00 | 1.047 | offpeak | int | 0.08616 | 0.08468 | 0.05209 |
2011-01-21 16:00:00 | 0.959 | offpeak | int | 0.08616 | 0.08468 | 0.05209 |
2011-01-21 17:00:00 | 0.911 | peak | peak | 0.08616 | 0.11924 | 0.18266 |
2011-01-21 18:00:00 | 0.914 | peak | peak | 0.08616 | 0.11924 | 0.18266 |
2011-01-21 19:00:00 | 0.932 | peak | peak | 0.08616 | 0.11924 | 0.18266 |
2011-01-21 20:00:00 | 0.927 | peak | peak | 0.08616 | 0.11924 | 0.18266 |
2011-01-21 21:00:00 | 0.859 | offpeak | offpeak | 0.08616 | 0.06974 | 0.05209 |
2011-01-21 22:00:00 | 0.862 | offpeak | offpeak | 0.08616 | 0.06974 | 0.05209 |
2011-01-21 23:00:00 | 0.888 | offpeak | offpeak | 0.08616 | 0.06974 | 0.05209 |
demand_data['BGE-EV'].plot()
--------------------------------------------------------------------------- TypeError Traceback (most recent call last) <ipython-input-31-38517ef7470b> in <module>() ----> 1 demand_data['BGE-EV'].plot() /Library/Frameworks/Python.framework/Versions/7.3/lib/python2.7/site-packages/pandas-0.12.0-py2.7-macosx-10.5-i386.egg/pandas/tools/plotting.pyc in plot_series(series, label, kind, use_index, rot, xticks, yticks, xlim, ylim, ax, style, grid, legend, logx, logy, secondary_y, **kwds) 1728 secondary_y=secondary_y, **kwds) 1729 -> 1730 plot_obj.generate() 1731 plot_obj.draw() 1732 /Library/Frameworks/Python.framework/Versions/7.3/lib/python2.7/site-packages/pandas-0.12.0-py2.7-macosx-10.5-i386.egg/pandas/tools/plotting.pyc in generate(self) 852 def generate(self): 853 self._args_adjust() --> 854 self._compute_plot_data() 855 self._setup_subplots() 856 self._make_plot() /Library/Frameworks/Python.framework/Versions/7.3/lib/python2.7/site-packages/pandas-0.12.0-py2.7-macosx-10.5-i386.egg/pandas/tools/plotting.pyc in _compute_plot_data(self) 936 # still an object dtype so we can't plot it 937 if numeric_data.dtype == np.object_: --> 938 raise TypeError('Series has object dtype and cannot be' 939 ' converted: no numeric data to plot') 940 TypeError: Series has object dtype and cannot be converted: no numeric data to plot
a = demand_data
a['BGE-EV'] = 'offpeak'
a['BGE-EV'].ix[(a[a.index.weekday<5].between_time('7:00','10:00')).index] = 'peak'
a['BGE-EV'].ix[(a[a.index.weekday<5].between_time('17:00','21:00')).index] = 'peak'
a[40:72]
USAGE | BGE-EV | |
---|---|---|
2011-01-03 00:00:00 | 1.090 | offpeak |
2011-01-03 01:00:00 | 1.405 | offpeak |
2011-01-03 02:00:00 | 1.500 | offpeak |
2011-01-03 03:00:00 | 1.404 | offpeak |
2011-01-03 04:00:00 | 1.314 | offpeak |
2011-01-03 05:00:00 | 1.247 | offpeak |
2011-01-03 06:00:00 | 1.089 | offpeak |
2011-01-03 07:00:00 | 0.924 | peak |
2011-01-03 08:00:00 | 0.808 | peak |
2011-01-03 09:00:00 | 0.748 | peak |
2011-01-03 10:00:00 | 0.714 | peak |
2011-01-03 11:00:00 | 0.690 | offpeak |
2011-01-03 12:00:00 | 0.711 | offpeak |
2011-01-03 13:00:00 | 0.829 | offpeak |
2011-01-03 14:00:00 | 0.964 | offpeak |
2011-01-03 15:00:00 | 0.962 | offpeak |
2011-01-03 16:00:00 | 1.050 | offpeak |
2011-01-03 17:00:00 | 1.096 | peak |
2011-01-03 18:00:00 | 1.111 | peak |
2011-01-03 19:00:00 | 1.127 | peak |
2011-01-03 20:00:00 | 1.165 | peak |
2011-01-03 21:00:00 | 1.055 | peak |
2011-01-03 22:00:00 | 1.007 | offpeak |
2011-01-03 23:00:00 | 0.982 | offpeak |
2011-01-04 00:00:00 | 1.057 | offpeak |
2011-01-04 01:00:00 | 1.399 | offpeak |
2011-01-04 02:00:00 | 1.532 | offpeak |
2011-01-04 03:00:00 | 1.444 | offpeak |
2011-01-04 04:00:00 | 1.445 | offpeak |
2011-01-04 05:00:00 | 1.275 | offpeak |
2011-01-04 06:00:00 | 1.040 | offpeak |
2011-01-04 07:00:00 | 0.843 | peak |
a = 2
del a
a
--------------------------------------------------------------------------- NameError Traceback (most recent call last) <ipython-input-78-60b725f10c9c> in <module>() ----> 1 a NameError: name 'a' is not defined