Skip to content

Commit

Permalink
Merge branch 'release/0.3'
Browse files Browse the repository at this point in the history
  • Loading branch information
pksohn committed May 2, 2017
2 parents 5167072 + e95422b commit 571a9a3
Show file tree
Hide file tree
Showing 6 changed files with 505 additions and 357 deletions.
18 changes: 10 additions & 8 deletions .travis.yml
Original file line number Diff line number Diff line change
Expand Up @@ -15,18 +15,20 @@ install:
- conda update -q conda
- conda info -a
- |
conda create -q -n test-environment python=$TRAVIS_PYTHON_VERSION pip numpy pandas pytest matplotlib scipy statsmodels
conda create -q -n test-environment python=$TRAVIS_PYTHON_VERSION pip numpy pandas pytest matplotlib scipy statsmodels pytables
- source activate test-environment
- conda list
- pip install https://github.com/UDST/orca/archive/master.zip
- pip install https://github.com/pksohn/urbansim/archive/python3.zip
- if [[ "$TRAVIS_PYTHON_VERSION" == "2.7" ]]; then pip install pandana; else
pip install https://github.com/UDST/osmnet/archive/python3-support.zip &&
pip install https://github.com/UDST/pandana/archive/python3-support.zip; fi
- pip install pycodestyle
- pip install orca
- pip install https://github.com/udst/urbansim/archive/master.zip
- pip install osmnet pandana
- pip install .
- cd .. && git clone [email protected]:urbansim/urbansim_parcels.git
- pip install ./urbansim_parcels
- cd "$TRAVIS_BUILD_DIR"

script:
- cd "$TRAVIS_BUILD_DIR" && py.test
- cd ../urbansim_parcels/sf_example && python simulate.py
- pycodestyle developer
- py.test
- cd ../urbansim_parcels/sf_example && python simulate.py
- cd ../sd_example && python Simulation.py
2 changes: 1 addition & 1 deletion developer/__init__.py
Original file line number Diff line number Diff line change
@@ -1 +1 @@
__version__ = '0.2.0'
__version__ = '0.3.0'
42 changes: 32 additions & 10 deletions developer/develop.py
Original file line number Diff line number Diff line change
Expand Up @@ -153,7 +153,7 @@ def to_yaml(self, str_or_buffer=None):
logger.debug('serializing Developer model to YAML')
return utils.convert_to_yaml(self.to_dict, str_or_buffer)

def pick(self, profit_to_prob_func=None):
def pick(self, profit_to_prob_func=None, custom_selection_func=None):
"""
Choose the buildings from the list that are feasible to build in
order to match the specified demand.
Expand All @@ -166,6 +166,11 @@ def pick(self, profit_to_prob_func=None):
a function which takes the feasibility dataframe and returns
a series of probabilities. If no function is passed, the behavior
of this method will not change
custom_selection_func: func
User passed function that decides how to select buildings for
development after probabilities are calculated. Must have
parameters (self, df, p) and return a numpy array of buildings to
build (i.e. df.index.values)
Returns
-------
Expand All @@ -174,26 +179,28 @@ def pick(self, profit_to_prob_func=None):
DataFrame of buildings to add. These buildings are rows from the
DataFrame that is returned from feasibility.
"""
df = self.feasibility
empty_warn = "WARNING THERE ARE NO FEASIBLE BUILDINGS TO CHOOSE FROM"

if len(self.feasibility) == 0:
# no feasible buildings, might as well bail
if len(df) == 0 or df.empty:
print(empty_warn)
return

# Get DataFrame of potential buildings from SqFtProForma steps
df = self._get_dataframe_of_buildings()
df = self._remove_infeasible_buildings(df)
df = self._calculate_net_units(df)

if len(df) == 0:
print("WARNING THERE ARE NO FEASIBLE BUILDING TO CHOOSE FROM")
if len(df) == 0 or df.empty:
print(empty_warn)
return

print("Sum of net units that are profitable: {:,}".format(
int(df.net_units.sum())))

# Generate development probabilities and pick buildings to build
p, df = self._calculate_probabilities(df, profit_to_prob_func)
build_idx = self._buildings_to_build(df, p)
build_idx = self._select_buildings(df, p, custom_selection_func)

# Drop built buildings from self.feasibility attribute if desired
self._drop_built_buildings(build_idx)
Expand Down Expand Up @@ -295,6 +302,8 @@ def _remove_infeasible_buildings(self, df):
-------
df : DataFrame
"""
if len(df) == 0 or df.empty:
return df

df = df[df.max_profit_far > 0]
self.ave_unit_size[
Expand Down Expand Up @@ -326,6 +335,8 @@ def _calculate_net_units(self, df):
-------
df : DataFrame
"""
if len(df) == 0 or df.empty:
return df

if self.residential:
df['net_units'] = df.residential_units - df.current_units
Expand Down Expand Up @@ -362,7 +373,7 @@ def _calculate_probabilities(df, profit_to_prob_func):
p = df.max_profit_per_size.values / df.max_profit_per_size.sum()
return p, df

def _buildings_to_build(self, df, p):
def _select_buildings(self, df, p, custom_selection_func):
"""
Helper method to pick(). Selects buildings to build based on
development probabilities.
Expand All @@ -373,6 +384,11 @@ def _buildings_to_build(self, df, p):
DataFrame of buildings from _calculate_probabilities method
p : Series
Probabilities from _calculate_probabilities method
custom_selection_func: func
User passed function that decides how to select buildings for
development after probabilities are calculated. Must have
parameters (self, df, p) and return a numpy array of buildings to
build (i.e. df.index.values)
Returns
-------
Expand All @@ -381,7 +397,9 @@ def _buildings_to_build(self, df, p):
"""

if df.net_units.sum() < self.target_units:
if custom_selection_func is not None:
build_idx = custom_selection_func(self, df, p)
elif df.net_units.sum() < self.target_units:
print("WARNING THERE WERE NOT ENOUGH PROFITABLE UNITS TO",
"MATCH DEMAND")
build_idx = df.index.values
Expand Down Expand Up @@ -442,7 +460,11 @@ def _prepare_new_buildings(self, df, build_idx):
"""

new_df = df.loc[build_idx]
new_df.index.name = "parcel_id"

drop = True
if 'parcel_id' not in df.columns:
new_df.index.name = "parcel_id"
drop = False

if self.year is not None:
new_df["year_built"] = self.year
Expand All @@ -453,4 +475,4 @@ def _prepare_new_buildings(self, df, build_idx):

new_df["stories"] = new_df.stories.apply(np.ceil)

return new_df.reset_index()
return new_df.reset_index(drop=drop)
Loading

0 comments on commit 571a9a3

Please sign in to comment.