def __call__(self, point): if not isinstance(point, dict): raise FuncDesignerException('argument should be Python dictionary') if not isinstance(point, ooPoint): point = ooPoint(point) r = ooSystemState([(elem, simplify(elem(point))) for elem in self.items]) # handling constraints #!!!!!!!!!!!!!!!!!!! TODO: perform attached constraints lookup only once if ooSystem wasn't modified by += or &= etc cons = self._getAllConstraints() activeConstraints = [] allAreFinite = all( [all(isfinite(asarray(elem(point)))) for elem in self.items]) for c in cons: val = c.oofun(point) if c(point) is False or any(isnan(atleast_1d(val))): activeConstraints.append(c) #_activeConstraints.append([c, val, max((val-c.ub, c.lb-val)), c.tol]) r.isFeasible = True if len( activeConstraints) == 0 and allAreFinite else False #r._activeConstraints = activeConstraints r.activeConstraints = activeConstraints return r
def __call__(self, point): if not isinstance(point, dict): raise FuncDesignerException('argument should be Python dictionary') if not isinstance(point, ooPoint): point = ooPoint(point) r = ooSystemState([(elem, simplify(elem(point))) for elem in self.items]) # handling constraints #!!!!!!!!!!!!!!!!!!! TODO: perform attached constraints lookup only once if ooSystem wasn't modified by += or &= etc cons = self._getAllConstraints() activeConstraints = [] allAreFinite = all([all(isfinite(asarray(elem(point)))) for elem in self.items]) for c in cons: val = c.oofun(point) if c(point) is False or any(isnan(atleast_1d(val))): activeConstraints.append(c) #_activeConstraints.append([c, val, max((val-c.ub, c.lb-val)), c.tol]) r.isFeasible = True if len(activeConstraints) == 0 and allAreFinite else False #r._activeConstraints = activeConstraints r.activeConstraints = activeConstraints return r
def vector2point(S, x): isComplexArray = isinstance(x, ndarray) and str(x.dtype).startswith('complex') x = atleast_1d(array(x, copy=True) if isComplexArray else array(x, copy=True, dtype=float)) if array_equal(x, S._SavedValues['prevX']): return S._SavedValues['prevVal'] # without copy() ipopt and probably others can replace it by noise after closing kw = {'skipArrayCast':True} if isComplexArray else {} r = ooPoint((v, x[S.oovar_indexes[i]:S.oovar_indexes[i+1]]) for i, v in enumerate(S._variables), **kw) S._SavedValues['prevVal'] = r S._SavedValues['prevX'] = copy(x) return r
def nlh(self, Lx, Ux, p, dataType): m = Lx.shape[0] # is changed in the cycle if m == 0: assert 0, 'bug in FuncDesigner' #return None, None, None tol = self.tol if self.tol > 0.0 else p.contol if self.tol == 0 else 0.0 # 0 for negative tolerances # TODO: check it if p.solver.dataHandling == 'sorted': tol = 0 selfDep = (self.oofun._getDep() if not self.oofun.is_oovar else set([self.oofun])) # TODO: improve it domainData = [(v, (Lx[:, k], Ux[:, k])) for k, v in enumerate(p._freeVarsList) if v in selfDep] domain = ooPoint(domainData, skipArrayCast=True) domain.isMultiPoint = True domain.dictOfFixedFuncs = p.dictOfFixedFuncs r, r0 = self.oofun.iqg(domain, dataType, self.lb, self.ub) Lf, Uf = r0.lb, r0.ub tmp = getSmoothNLH(tile(Lf, (2, 1)), tile(Uf, (2, 1)), self.lb, self.ub, tol, m, dataType) T02 = tmp T0 = T02[:, tmp.shape[1]/2:].flatten() res = {} if len(r): dep = selfDep.intersection(domain.keys()) # TODO: Improve it for v in dep: Lf, Uf = vstack((r[v][0].lb, r[v][1].lb)), vstack((r[v][0].ub, r[v][1].ub)) # TODO: 1) FIX IT it for matrix definiteRange # 2) seems like DefiniteRange = (True, True) for any variable is enough for whole range to be defined in the involved node # DefiniteRange = logical_and(DefiniteRange, r[v][0].definiteRange) # DefiniteRange = logical_and(DefiniteRange, r[v][1].definiteRange) tmp = getSmoothNLH(Lf, Uf, self.lb, self.ub, tol, m, dataType) #- T02 #tmp[isnan(tmp)] = inf res[v] = tmp return T0, res, r0.definiteRange
def iqg(Self, domain, dtype = float, lb=None, ub=None, UB = None): if type(domain) != ooPoint: domain = ooPoint(domain, skipArrayCast=True) domain.isMultiPoint=True domain.useSave = True r0 = Self.interval(domain, dtype, resetStoredIntervals = False) r0.lb, r0.ub = atleast_1d(r0.lb).copy(), atleast_1d(r0.ub).copy() # is copy required? # TODO: get rid of useSave domain.useSave = False # TODO: rework it with indexation of required data if lb is not None and ub is not None: ind = logical_or(logical_or(r0.ub < lb, r0.lb > ub), all(logical_and(r0.lb >= lb, r0.ub <= ub))) elif UB is not None: ind = r0.lb > UB else: ind = None useSlicing = False if ind is not None: if all(ind): return {}, r0 j = where(~ind)[0] #DOESN'T WORK FOR FIXED OOVARS AND DefiniteRange != TRUE YET if 0 and j.size < 0.85*ind.size: # at least 15% of values to skip useSlicing = True tmp = [] for key, val in domain.storedIntervals.items(): Interval, definiteRange = val if type(definiteRange) not in (bool, bool_): definiteRange = definiteRange[j] tmp.append((key, (Interval[:, j], definiteRange))) _storedIntervals = dict(tmp) Tmp = [] for key, val in domain.storedSums.items(): # TODO: rework it R0, DefiniteRange0 = val.pop(-1) #R0, DefiniteRange0 = val[-1] R0 = R0[:, j] if type(DefiniteRange0) not in (bool, bool_): DefiniteRange0 = DefiniteRange0[j] tmp = [] for k,v in val.items(): # TODO: rework it # if k is (-1): continue v = v[:, j] tmp.append((k,v)) val = dict(tmp) val[-1] = (R0, DefiniteRange0) Tmp.append((key,val)) _storedSums = dict(Tmp) #domain.storedSums = dict(tmp) Tmp = [] for key, val in domain.items(): lb_,ub_ = val # TODO: rework it when lb, ub will be implemented as 2-dimensional Tmp.append((key, (lb_[j],ub_[j]))) dictOfFixedFuncs = domain.dictOfFixedFuncs domain2 = ooPoint(Tmp, skipArrayCast=True) domain2.storedSums = _storedSums domain2.storedIntervals = _storedIntervals domain2.dictOfFixedFuncs = dictOfFixedFuncs domain2.isMultiPoint=True domain = domain2 domain.useAsMutable = True r = {} Dep = (Self._getDep() if not Self.is_oovar else set([Self])).intersection(domain.keys()) for i, v in enumerate(Dep): domain.modificationVar = v r_l, r_u = _iqg(Self, domain, dtype, r0) if useSlicing and r_l is not r0:# r_l is r0 when array_equal(lb, ub) lf1, lf2, uf1, uf2 = r_l.lb, r_u.lb, r_l.ub, r_u.ub Lf1, Lf2, Uf1, Uf2 = Copy(r0.lb), Copy(r0.lb), Copy(r0.ub), Copy(r0.ub) Lf1[:, j], Lf2[:, j], Uf1[:, j], Uf2[:, j] = lf1, lf2, uf1, uf2 r_l.lb, r_u.lb, r_l.ub, r_u.ub = Lf1, Lf2, Uf1, Uf2 if type(r0.definiteRange) not in (bool, bool_): d1, d2 = r_l.definiteRange, r_u.definiteRange D1, D2 = atleast_1d(r0.definiteRange).copy(), atleast_1d(r0.definiteRange).copy() D1[j], D2[j] = d1, d2 r_l.definiteRange, r_u.definiteRange = D1, D2 r[v] = r_l, r_u if not Self.isUncycled: lf1, lf2, uf1, uf2 = r_l.lb, r_u.lb, r_l.ub, r_u.ub lf, uf = nanmin(vstack((lf1, lf2)), 0), nanmax(vstack((uf1, uf2)), 0) if i == 0: L, U = lf.copy(), uf.copy() else: L[L<lf] = lf[L<lf].copy() U[U>uf] = uf[U>uf].copy() if not Self.isUncycled: for R in r.values(): r1, r2 = R if type(r1.lb) != np.ndarray: r1.lb, r2.lb, r1.ub, r2.ub = atleast_1d(r1.lb), atleast_1d(r2.lb), atleast_1d(r1.ub), atleast_1d(r2.ub) r1.lb[r1.lb < L] = L[r1.lb < L] r2.lb[r2.lb < L] = L[r2.lb < L] r1.ub[r1.ub > U] = U[r1.ub > U] r2.ub[r2.ub > U] = U[r2.ub > U] r0.lb[r0.lb < L] = L[r0.lb < L] r0.ub[r0.ub > U] = U[r0.ub > U] # for more safety domain.useSave = True domain.useAsMutable = False domain.modificationVar = None domain.storedIntervals = {} return r, r0
def iqg(Self, domain, dtype=float, lb=None, ub=None, UB=None): if type(domain) != ooPoint: domain = ooPoint(domain, skipArrayCast=True) domain.isMultiPoint = True domain.useSave = True r0 = Self.interval(domain, dtype, resetStoredIntervals=False) r0.lb, r0.ub = atleast_1d(r0.lb).copy(), atleast_1d( r0.ub).copy() # is copy required? # TODO: get rid of useSave domain.useSave = False # TODO: rework it with indexation of required data if lb is not None and ub is not None: ind = logical_or(logical_or(r0.ub < lb, r0.lb > ub), all(logical_and(r0.lb >= lb, r0.ub <= ub))) elif UB is not None: ind = r0.lb > UB else: ind = None useSlicing = False if ind is not None: if all(ind): return {}, r0 j = where(~ind)[0] #DOESN'T WORK FOR FIXED OOVARS AND DefiniteRange != TRUE YET if 0 and j.size < 0.85 * ind.size: # at least 15% of values to skip useSlicing = True tmp = [] for key, val in domain.storedIntervals.items(): Interval, definiteRange = val if type(definiteRange) not in (bool, bool_): definiteRange = definiteRange[j] tmp.append((key, (Interval[:, j], definiteRange))) _storedIntervals = dict(tmp) Tmp = [] for key, val in domain.storedSums.items(): # TODO: rework it R0, DefiniteRange0 = val.pop(-1) #R0, DefiniteRange0 = val[-1] R0 = R0[:, j] if type(DefiniteRange0) not in (bool, bool_): DefiniteRange0 = DefiniteRange0[j] tmp = [] for k, v in val.items(): # TODO: rework it # if k is (-1): continue v = v[:, j] tmp.append((k, v)) val = dict(tmp) val[-1] = (R0, DefiniteRange0) Tmp.append((key, val)) _storedSums = dict(Tmp) #domain.storedSums = dict(tmp) Tmp = [] for key, val in domain.items(): lb_, ub_ = val # TODO: rework it when lb, ub will be implemented as 2-dimensional Tmp.append((key, (lb_[j], ub_[j]))) dictOfFixedFuncs = domain.dictOfFixedFuncs domain2 = ooPoint(Tmp, skipArrayCast=True) domain2.storedSums = _storedSums domain2.storedIntervals = _storedIntervals domain2.dictOfFixedFuncs = dictOfFixedFuncs domain2._dictOfRedirectedFuncs = domain._dictOfRedirectedFuncs domain2.nPoints = domain.nPoints domain2.isMultiPoint = True domain = domain2 domain.useAsMutable = True r = {} Dep = (Self._getDep() if not Self.is_oovar else set([Self])).intersection( domain.keys()) for i, v in enumerate(Dep): domain.modificationVar = v r_l, r_u = _iqg(Self, domain, dtype, r0) if useSlicing and r_l is not r0: # r_l is r0 when array_equal(lb, ub) lf1, lf2, uf1, uf2 = r_l.lb, r_u.lb, r_l.ub, r_u.ub Lf1, Lf2, Uf1, Uf2 = Copy(r0.lb), Copy(r0.lb), Copy(r0.ub), Copy( r0.ub) Lf1[:, j], Lf2[:, j], Uf1[:, j], Uf2[:, j] = lf1, lf2, uf1, uf2 r_l.lb, r_u.lb, r_l.ub, r_u.ub = Lf1, Lf2, Uf1, Uf2 if type(r0.definiteRange) not in (bool, bool_): d1, d2 = r_l.definiteRange, r_u.definiteRange D1, D2 = atleast_1d(r0.definiteRange).copy(), atleast_1d( r0.definiteRange).copy() D1[j], D2[j] = d1, d2 r_l.definiteRange, r_u.definiteRange = D1, D2 r[v] = r_l, r_u if not Self.isUncycled: lf1, lf2, uf1, uf2 = r_l.lb, r_u.lb, r_l.ub, r_u.ub lf, uf = nanmin(vstack((lf1, lf2)), 0), nanmax(vstack((uf1, uf2)), 0) if i == 0: L, U = lf.copy(), uf.copy() else: L[L < lf] = lf[L < lf].copy() U[U > uf] = uf[U > uf].copy() if not Self.isUncycled: for R in r.values(): r1, r2 = R if type(r1.lb) != np.ndarray: r1.lb, r2.lb, r1.ub, r2.ub = atleast_1d(r1.lb), atleast_1d( r2.lb), atleast_1d(r1.ub), atleast_1d(r2.ub) r1.lb[r1.lb < L] = L[r1.lb < L] r2.lb[r2.lb < L] = L[r2.lb < L] r1.ub[r1.ub > U] = U[r1.ub > U] r2.ub[r2.ub > U] = U[r2.ub > U] r0.lb[r0.lb < L] = L[r0.lb < L] r0.ub[r0.ub > U] = U[r0.ub > U] # for more safety domain.useSave = True domain.useAsMutable = False domain.modificationVar = None domain.storedIntervals = {} return r, r0