def apply_primal_simplex(self, basis_map): ''' Applies primal simplex to the matrix using a feasible basis. ''' M = self.Mx h, w = M.shape try: # Check input basis self.check_basis_map(basis_map) # Apply pivoting loop using primal pivot picker self.pivoting_loop(self.pick_primal_pivot, basis_map) # Setup optimal result self.setup_optimal_result(basis_map) status = Status.OPTIMAL except UnboundedException as e: # LP is unbounded. # Build unboundedness certificate. idx = self.neg_col self.cert = np.matrix([ff(0)] * (w - h)) self.cert[0, idx - h + 1] = ff(1) for row in basis_map: self.cert[0, basis_map[row] - h + 1] = -M[row, idx] self.cert = self.cert[0, :-h + 1] status = Status.UNBOUNDED return status
def add_restriction(self, restriction_row, basis_map, slack=0): ''' Adds a new restriction to an already found solution. slack may be set to 0 (=), 1 (<=) or -1 (>=). ''' if self.opt_val is None: return h, w = self.Mx.shape # Add the restriction and slack variables. slack_col = np.matrix(np.zeros(shape=(h + 1, 1), dtype='object')) slack_col[-1, 0] = ff(slack) self.Mx = np.concatenate([self.Mx, restriction_row]) self.Mx = np.concatenate([ self.Mx[:, :h - 1], slack_col, self.Mx[:, h - 1:-1], slack_col, self.Mx[:, -1] ], axis=1) if self.debug: print('[Add restriction (' + str(slack) + ')]', StdLP.printable(restriction_row)) print(self) basis_map[h] = w - 1 for row in basis_map: basis_map[row] += 1
def append_log(A): ''' Appends the logging matrix to the tableau. ''' h, w = A.shape log = np.concatenate( (np.matrix([ff(0)] * (h - 1)), StdLP.fidentity(h - 1)), axis=0) return np.concatenate((log, A), axis=1)
def apply_cutting_plane(self, basis_map): ''' Applies the cutting plane method to solve the integer programming problem. ''' # Apply simplex to linear relaxation. status = self.apply_simplex(basis_map) # Cancel method if not optimal if status != Status.OPTIMAL: return status # Save results for linear relaxation. self.lr_cert = self.cert.copy() self.lr_opt_vec = self.opt_vec.copy() self.lr_opt_val = self.opt_val last = status integer = False c = 1 while not integer: # Get dimensions. h, w = self.Mx.shape # Assume this is the last iteration of the loop. integer = True for y in range(1, h): # Skip integer entries and slack variables if self.Mx[y, -1].denominator == 1 or basis_map[y] >= w - h: continue # Break loop assumption. integer = False # Pick fractional entry. row = y print('[Cutting plane', c, 'for row ' + str(row) + ']') # Build restriction. restriction = self.Mx[row, :].copy() for x in range(w): if x >= h - 1: restriction[0, x] = ff(floor(restriction[0, x])) else: restriction[0, x] = 0 # Enforce restriction on existing solution. self.add_restriction(restriction, basis_map, slack=1) last = self.restore_solution_after_restriction(basis_map) print('[Optimal]', self.Mx[0, -1]) if self.debug: print(self) c += 1 return last
def build_aux(M): ''' Builds the auxiliary tableau. ''' h, w = M.shape # Clear target function. M[0] -= M[0] # Appended matrix aux = np.concatenate( (np.matrix([ff(1)] * (h - 1)), StdLP.fidentity(h - 1)), axis=0) new_M = np.concatenate((M[:, :-1], aux, M[:, -1]), axis=1) return new_M
def setup_optimal_result(self, basis_map): ''' Sets up the optimal result given a final tableau and the basis. ''' h, w = self.Mx.shape # Optimal value. self.opt_val = self.Mx[0, -1] # Optimal vector. self.opt_vec = np.matrix([ff(0)] * w) for row in basis_map: self.opt_vec[0, basis_map[row]] = self.Mx[row, -1] # Delete log and slack entries from optimal vector. self.opt_vec = self.opt_vec[0, h - 1:-h] # Certificate of optimality. self.cert = self.Mx[0, :h - 1]
def fidentity(n): ''' Identity matrix of Fraction objects. ''' return np.identity(n, dtype='object') + ff()
def _apply_bb_rec(self, Mo, basis_map, lvl=0): ''' Heavy work for recursive branch and bound. ''' M = Mo.copy() h, w = M.shape for row in range(1, h): # Skip integer entries. if M[row, -1].denominator == 1: continue # Skip slack variables. col = basis_map[row] if col >= w - h: continue # Build 1st restriction r1 = M[row, :].copy() for x in range(w): r1[0, x] = ff(0) r1[0, col] = ff(1) r1[0, -1] = ff(floor(M[row, -1])) print((' ' * lvl) + '[Branch] x_' + str(col - h + 1) + ' <= ' + str(r1[0, -1])) # Copy basis and input matrix basis = dict() basis.update(basis_map) self.Mx = M.copy() # Add 1st restriction self.add_restriction(r1, basis, slack=1) # Restore basis (optimized, just need to pivot branch var) self.pivot(row, basis[row]) # Restore solution if needed status = self.apply_dual_simplex(basis) if self.debug: print(self) # Left branch if status == Status.OPTIMAL: if not self.bb_best_val or self.opt_val > self.bb_best_val: if StdLP.all_integer(self.opt_vec): # Update solution self.bb_best_val = self.opt_val self.bb_best_vec = self.opt_vec else: # Explore branch self._apply_bb_rec(self.Mx, basis, lvl=lvl + 1) print((' ' * lvl) + '[Optimal]', self.bb_best_val) else: # Prune branch print((' ' * lvl) + '[Pruned]') # Build 2nd restriction r2 = M[row, :].copy() for x in range(w): r2[0, x] = ff(0) r2[0, col] = ff(1) r2[0, -1] = ff(ceil(M[row, -1])) print((' ' * lvl) + '[Branch] x_' + str(col - h + 1) + ' >= ' + str(r2[0, -1])) # Copy basis and input matrix basis = dict() basis.update(basis_map) self.Mx = M.copy() # Add 2nd restriction self.add_restriction(r2, basis, slack=-1) # Restore basis (optimized, just need to pivot branch var and slack) self.pivot(row, basis[row]) self.pivot(h, w) # Restore solution if needed status = self.apply_dual_simplex(basis) if self.debug: print(self) print('[' + str(status) + ']') # Right branch if status == Status.OPTIMAL: if not self.bb_best_val or self.opt_val > self.bb_best_val: if StdLP.all_integer(self.opt_vec): # Update solution self.bb_best_val = self.opt_val self.bb_best_vec = self.opt_vec else: # Explore branch self._apply_bb_rec(self.Mx, basis, lvl=lvl + 1) print((' ' * lvl) + '[Optimal]', self.opt_val) else: # Prune branch print((' ' * lvl) + '[Pruned]', self.opt_val, '<=', self.bb_best_val)
if len(sys.argv) < 2: fin = sys.stdin else: infile = sys.argv[1] fin = open(infile) # Input. m = int(fin.readline()) n = int(fin.readline()) matrix_line = fin.readline().strip() # Build input matrix & canonical basis. matrix = np.matrix(matrix_line, dtype='object').reshape(m + 1, n + 1) for i in range(0, m + 1): for j in range(0, n + 1): matrix[i, j] = ff(matrix[i, j]) A = matrix[1:] c = matrix[0] std_A, std_c = StdLP.leq_to_std(A, c) std_matrix = np.concatenate((-std_c, std_A), axis=0) # Initial basis from slack variables basis_map = {} for i in range(1, m + 1): basis_map[i] = m + n + i - 1 # Instantiate LP problem. problem = StdLP(std_matrix, logfile='pivoting.txt', debug=False,
Kurtosis = E[(X - mu)^4] / ( E[(X-mu)^2] )^2 ''' this_numerator = central_moment(pms, 4) this_denominator = (population_variance(pms)) ** 2 return this_numerator / this_denominator def coefficient_of_variation(pms): ''' Compute standard deviation / mean ''' return sqrt(population_variance(pms)) / raw_moment(pms, 1) six_pdf = [ [2, ff(2048,2 ** 17)], [3, ff(12288,2 ** 17)], [4, ff(16512,2 ** 17)], [5, ff(18432,2 ** 17)], [6, ff(20976,2 ** 17)], [7, ff(16464,2 ** 17)], [8, ff(14796,2 ** 17)], [9, ff(11220,2 ** 17)], [10, ff(7168,2 ** 17)], [11, ff(5172,2 ** 17)], [12, ff(3031,2 ** 17)], [13, ff(1495,2 ** 17)], [14, ff(831,2 ** 17)], [15, ff(407,2 ** 17)], [16, ff(161,2 ** 17)], [17, ff(57,2 ** 17)],