Commit 035d583c authored by Martin Reinecke's avatar Martin Reinecke
Browse files

Merge remote-tracking branch 'origin/NIFTy_5' into getting_started_3_improvements

parents 74da7292 19b88aac
......@@ -34,7 +34,8 @@ __all__ = ["ntask", "rank", "master", "local_shape", "data_object", "full",
"distaxis", "from_local_data", "from_global_data", "to_global_data",
"redistribute", "default_distaxis", "is_numpy", "absmax", "norm",
"lock", "locked", "uniform_full", "transpose", "to_global_data_rw",
"ensure_not_distributed", "ensure_default_distributed"]
"ensure_not_distributed", "ensure_default_distributed",
"clipped_exp"]
_comm = MPI.COMM_WORLD
ntask = _comm.Get_size()
......@@ -303,6 +304,10 @@ for f in ["sqrt", "exp", "log", "tanh", "conjugate"]:
setattr(_current_module, f, func(f))
def clipped_exp(a):
return data_object(x.shape, np.exp(np.clip(x.data, -300, 300), x.distaxis))
def from_object(object, dtype, copy, set_locked):
if dtype is None:
dtype = object.dtype
......
......@@ -33,7 +33,8 @@ __all__ = ["ntask", "rank", "master", "local_shape", "data_object", "full",
"distaxis", "from_local_data", "from_global_data", "to_global_data",
"redistribute", "default_distaxis", "is_numpy", "absmax", "norm",
"lock", "locked", "uniform_full", "to_global_data_rw",
"ensure_not_distributed", "ensure_default_distributed"]
"ensure_not_distributed", "ensure_default_distributed",
"clipped_exp"]
ntask = 1
rank = 0
......@@ -149,3 +150,7 @@ def absmax(arr):
def norm(arr, ord=2):
return np.linalg.norm(arr.reshape(-1), ord=ord)
def clipped_exp(arr):
return np.exp(np.clip(arr, -300, 300))
......@@ -102,11 +102,13 @@ class LogRGSpace(StructuredDomain):
dist = self.bindistances
for i in range(ndim):
ks = np.zeros(self.shape[i])
ks[1:] = np.minimum(self.shape[i] - 1 - np.arange(self.shape[i]-1), np.arange(self.shape[i]-1)) * dist[i]
ks[1:] = np.minimum(self.shape[i] - 1 - np.arange(self.shape[i]-1),
np.arange(self.shape[i]-1)) * dist[i]
if self.harmonic:
ks[0] = np.nan
else:
ks[0] = -np.inf
ks[1:] += self.t_0[i]
k_array[i] += ks.reshape((1,)*i + (self.shape[i],) + (1,)*(ndim-i-1))
k_array[i] += ks.reshape((1,)*i + (self.shape[i],)
+ (1,)*(ndim-i-1))
return k_array
......@@ -634,6 +634,9 @@ class Field(object):
def positive_tanh(self):
return 0.5*(1.+self.tanh())
def clipped_exp(self):
return Field(self._domain, dobj.clipped_exp(self._val))
def _binary_op(self, other, op):
# if other is a field, make sure that the domains match
f = getattr(self._val, op)
......
......@@ -183,6 +183,10 @@ class Linearization(object):
tmp = self._val.exp()
return self.new(tmp, makeOp(tmp)(self._jac))
def clipped_exp(self):
tmp = self._val.clipped_exp()
return self.new(tmp, makeOp(tmp)(self._jac))
def log(self):
tmp = self._val.log()
return self.new(tmp, makeOp(1./self._val)(self._jac))
......
......@@ -292,7 +292,7 @@ for op in ["__iadd__", "__isub__", "__imul__", "__idiv__",
setattr(MultiField, op, func(op))
for f in ["sqrt", "exp", "log", "tanh"]:
for f in ["sqrt", "exp", "log", "tanh", "clipped_exp"]:
def func(f):
def func2(self):
fu = getattr(Field, f)
......
......@@ -99,7 +99,7 @@ class Operator(NiftyMetaBase()):
return self.__class__.__name__
for f in ["sqrt", "exp", "log", "tanh", "positive_tanh"]:
for f in ["sqrt", "exp", "log", "tanh", "positive_tanh", 'clipped_exp']:
def func(f):
def func2(self):
fa = _FunctionApplier(self.target, f)
......
......@@ -38,7 +38,8 @@ __all__ = ['PS_field', 'power_analyze', 'create_power_operator',
'create_harmonic_smoothing_operator', 'from_random',
'full', 'from_global_data', 'from_local_data',
'makeDomain', 'sqrt', 'exp', 'log', 'tanh', 'positive_tanh',
'conjugate', 'get_signal_variance', 'makeOp', 'domain_union']
'conjugate', 'get_signal_variance', 'makeOp', 'domain_union',
'get_default_codomain']
def PS_field(pspace, func):
......@@ -267,3 +268,31 @@ for f in ["sqrt", "exp", "log", "tanh", "positive_tanh", "conjugate"]:
return getattr(np, f)(x)
return func2
setattr(_current_module, f, func(f))
def get_default_codomain(domainoid, space=None):
"""For `RGSpace`, returns the harmonic partner domain.
For `DomainTuple`, returns a copy of the object in which the domain
indexed by `space` is substituted by its harmonic partner domain.
In this case, if `space` is None, it is set to 0 if the `DomainTuple`
contains exactly one domain.
Parameters
----------
domain: `RGSpace` or `DomainTuple`
Domain for which to constuct the default harmonic partner
space: int
Optional index of the subdomain to be replaced by its default
codomain. `domain[space]` must be of class `RGSpace`.
"""
from .domains.rg_space import RGSpace
if isinstance(domainoid, RGSpace):
return domainoid.get_default_codomain()
if not isinstance(domainoid, DomainTuple):
raise TypeError(
'Works only on RGSpaces and DomainTuples containing those')
space = utilities.infer_space(domainoid, space)
if not isinstance(domainoid[space], RGSpace):
raise TypeError("can only codomain RGSpaces")
ret = [dom for dom in domainoid]
ret[space] = domainoid[space].get_default_codomain()
return DomainTuple.make(ret)
......@@ -122,7 +122,8 @@ def parse_spaces(spaces, nspc):
def infer_space(domain, space):
if space is None:
if len(domain) != 1:
raise ValueError("need a Field with exactly one domain")
raise ValueError("'space' index must be given for objects based on"
" DomainTuples containing more than one domain")
space = 0
space = int(space)
if space < 0 or space >= len(domain):
......
Markdown is supported
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment