Skip to content
This repository has been archived by the owner on May 21, 2021. It is now read-only.

Commit

Permalink
Browse files Browse the repository at this point in the history
Added improve functionality.
  • Loading branch information
pauleanderson committed Mar 7, 2019
1 parent c2d1339 commit 0e653b6
Show file tree
Hide file tree
Showing 4 changed files with 71 additions and 10 deletions.
3 changes: 2 additions & 1 deletion pyrankability/__init__.py
Expand Up @@ -8,4 +8,5 @@
from . import pruning_paper
from . import pruning_paper_dask
from . import pruning_paper_dask2
from . import pruning_paper_dask3
from . import pruning_paper_dask3
from . import improve
63 changes: 63 additions & 0 deletions pyrankability/improve.py
@@ -0,0 +1,63 @@
import numpy as np

from . import lp

def greedy(D,l,verbose=False):
output_lines = []
D = np.copy(D) # Leave the original untouched
for niter in range(l):
n=D.shape[0]

k,P,X,Y,k2 = lp.lp(D)

mult = 100
X = np.round(X*mult)/mult
Y = np.round(Y*mult)/mult

T0 = np.zeros((n,n))
T1 = np.zeros((n,n))
inxs = np.where(D + D.transpose() == 0)
T0[inxs] = 1
inxs = np.where(D + D.transpose() == 2)
T1[inxs] = 1
T0[np.arange(n),np.arange(n)]= 0
T1[np.arange(n),np.arange(n)] = 0

DOM = D + X - Y

Madd=T0*DOM # note: DOM = P_> in paper
M1 = Madd # Copy Madd into M, % Madd identifies values >0 in P_> that have 0-tied values in D
M1[Madd<=0] = np.nan # Set anything <= 0 to NaN
min_inx = np.nanargmin(M1) # Find min value and index
bestlinktoadd_i, bestlinktoadd_j = np.unravel_index(min_inx,M1.shape) # adding (i,j) link associated with
# smallest nonzero value in Madd is likely to produce greatest improvement in rankability
minMadd = M1[bestlinktoadd_i, bestlinktoadd_j]

Mdelete=T1*DOM # note: DOM = P_> in paper
Mdelete=Mdelete*(Mdelete<1) # Mdelete identifies values <1 in P_> that have 1-tied values in D
bestlinktodelete_i, bestlinktodelete_j=np.unravel_index(np.nanargmax(Mdelete), Mdelete.shape) # deleting (i,j) link associated with
# largest non-unit (less than 1) value in Mdelete is likely to produce greatest improvement in rankability
maxMdelete = Mdelete[bestlinktodelete_i, bestlinktodelete_j]

# This next section modifies D to create Dtilde
Dtilde = np.copy(D) # initialize Dtilde
# choose whether to add or remove a link depending on which will have the biggest
# impact on reducing the size of the set P
# PAUL: Or if we only want to do link addition, you don't need to form
# Mdelete and find the largest non-unit value in it. And vice versa, if
# only link removal is desired, don't form Madd.
if (1-minMadd)>maxMdelete:
Dtilde[bestlinktoadd_i,bestlinktoadd_j]=1 # adds this link, creating one-mod Dtilde
formatSpec = 'The best one-link way to improve rankability is by adding a link from %d to %d.\nThis one modification removes about %.10f percent of the rankings in P.'%(bestlinktoadd_i,bestlinktoadd_j,(1-minMadd)*100)
if verbose:
print(formatSpec)
output_lines.append(formatSpec)
elif 1-minMadd<maxMdelete:
Dtilde[bestlinktodelete_i,bestlinktodelete_j] = 0 # removes this link, creating one-mod Dtilde
formatSpec = 'The best one-link way to improve rankability is by deleting the link from %d to %d.\nThis one modification removes about %.10f percent of the rankings in P.' % (bestlinktodelete_i,bestlinktodelete_j,maxMdelete*100)
if verbose:
print(formatSpec)
output_lines.append(formatSpec)

D = Dtilde
return D, "\n".join(output_lines)
13 changes: 5 additions & 8 deletions pyrankability/lp.py
Expand Up @@ -7,10 +7,7 @@
"""

import numpy as np
try:
from gurobipy import *
except:
pass
from gurobipy import *
import itertools

from .common import *
Expand Down Expand Up @@ -96,10 +93,10 @@ def _run(D,model,get_sol_x_func,get_sol_y_func,max_solutions,obj2k_func=lambda o
k2 = int(np.count_nonzero(get_sol_x_func())) + int(np.count_nonzero(get_sol_y_func()))

if max_solutions == None:
return k,[], get_sol_x_func(), get_sol_y_func(), k2

P = _get_P(D,model,get_sol_x_func,get_sol_y_func)
return k, P
P = []
else:
P = _get_P(D,model,get_sol_x_func,get_sol_y_func)
return k, P, get_sol_x_func(), get_sol_y_func(), k2

def round_Xn(Xn,mult=10):
return Xn #round(mult*Xn)*1./mult
Expand Down
2 changes: 1 addition & 1 deletion setup.py
Expand Up @@ -2,7 +2,7 @@

setuptools.setup(
name="pyrankability",
version="0.0.9",
version="0.0.11",
author="Paul Anderson",
author_email="pauleanderson@gmail.com",
description="Rankability Toolbox",
Expand Down

0 comments on commit 0e653b6

Please sign in to comment.