Skip to content

Commit

Permalink
Change clone to copy and add private _init_copy method
Browse files Browse the repository at this point in the history
  • Loading branch information
adonath committed Jul 23, 2018
1 parent 2c63297 commit 49e23a4
Show file tree
Hide file tree
Showing 10 changed files with 85 additions and 80 deletions.
2 changes: 1 addition & 1 deletion gammapy/cube/new.py
Original file line number Diff line number Diff line change
Expand Up @@ -215,7 +215,7 @@ def make_map_background_fov(acceptance_map, counts_map, exclusion_mask):

norm_bkg = norm_factor * acceptance_map.data.T

return acceptance_map.clone(data=norm_bkg.T)
return acceptance_map.copy(data=norm_bkg.T)


class MapMaker(object):
Expand Down
4 changes: 2 additions & 2 deletions gammapy/detect/kernel.py
Original file line number Diff line number Diff line change
Expand Up @@ -14,7 +14,7 @@
]


# TODO: use `Map.clone` or `Map.copy` once available
# TODO: use `Map.copy` or `Map.copy` once available
# instead of the awkward way with `Map.from_geom` and adjusting map data after.
class KernelBackgroundEstimator(object):
"""Estimate background and exclusion mask iteratively.
Expand Down Expand Up @@ -152,7 +152,7 @@ def _estimate_exclusion(self, counts, significance):
mask = (significance.data < self.parameters['significance_threshold']) | np.isnan(significance.data)
mask = binary_erosion(mask, structure, border_value=1)

return counts.clone(data=mask.astype('float'))
return counts.copy(data=mask.astype('float'))

def _estimate_background(self, counts, exclusion):
"""
Expand Down
20 changes: 10 additions & 10 deletions gammapy/detect/lima.py
Original file line number Diff line number Diff line change
Expand Up @@ -55,10 +55,10 @@ def compute_lima_image(counts, background, kernel, exposure=None):

# TODO: we should make coopies of the geom to make them independent objects
images = {
'significance': counts.clone(data=significance_conv),
'counts': counts.clone(data=counts_conv),
'background': counts.clone(data=background_conv),
'excess': counts.clone(data=excess_conv),
'significance': counts.copy(data=significance_conv),
'counts': counts.copy(data=counts_conv),
'background': counts.copy(data=background_conv),
'excess': counts.copy(data=excess_conv),
}

# TODO: should we be doing this here?
Expand Down Expand Up @@ -113,11 +113,11 @@ def compute_lima_on_off_image(n_on, n_off, a_on, a_off, kernel, exposure=None):
significance_conv = significance_on_off(n_on_conv, n_off.data, alpha_conv, method='lima')

images = {
'significance': n_on.clone(data=significance_conv),
'n_on': n_on.clone(data=n_on_conv),
'background': n_on.clone(data=background_conv),
'excess': n_on.clone(data=excess_conv),
'alpha': n_on.clone(data=alpha_conv),
'significance': n_on.copy(data=significance_conv),
'n_on': n_on.copy(data=n_on_conv),
'background': n_on.copy(data=background_conv),
'excess': n_on.copy(data=excess_conv),
'alpha': n_on.copy(data=alpha_conv),
}

# TODO: should we be doing this here?
Expand All @@ -137,4 +137,4 @@ def _add_other_images(images, exposure, kernel, conv_opt):
exposure_conv = convolve(exposure.data, kernel.array, **conv_opt)
flux = images['excess'].data / exposure_conv
# TODO: we should make coopies of the geom to make them independent objects
images['flux'] = images['excess'].clone(data=flux)
images['flux'] = images['excess'].copy(data=flux)
50 changes: 27 additions & 23 deletions gammapy/maps/base.py
Original file line number Diff line number Diff line change
Expand Up @@ -52,9 +52,22 @@ def __init__(self, geom, data, meta=None, unit=''):
self._unit = Unit(unit).to_string()

if meta is None:
self.meta = OrderedDict()
self._meta = OrderedDict()
else:
self.meta = OrderedDict(meta)
self._meta = OrderedDict(meta)

def _init_copy(self, **kwargs):
"""Init map instance by copying missing init arguments from self.
"""
argnames = inspect.getargspec(self.__init__).args
argnames.remove('self')
argnames.remove('dtype')

for arg in argnames:
value = getattr(self, '_' + arg)
kwargs.setdefault(arg, copy.deepcopy(value))

return self.__class__(**kwargs)

@property
def data(self):
Expand All @@ -71,6 +84,11 @@ def unit(self):
"""Map unit (`~astropy.units.Unit`)"""
return Unit(self._unit)

@property
def meta(self):
"""Map meta (`~OrderedDict`)"""
return self._meta

@data.setter
def data(self, val):
if val.shape != self.data.shape:
Expand Down Expand Up @@ -897,8 +915,8 @@ def set_by_idx(self, idx, vals):
"""
pass

def clone(self, **kwargs):
"""Clone map instance and overwrite given attributes.
def copy(self, **kwargs):
"""Copy map instance and overwrite given attributes, except for geometry.
Parameters
----------
Expand All @@ -907,26 +925,12 @@ def clone(self, **kwargs):
Returns
--------
clone : `Map`
Cloned Map.
copy : `Map`
Copied Map.
"""
init_args = inspect.getargspec(self.__init__).args
init_args.remove('self')
init_args.remove('dtype')

if 'geom' in kwargs and 'data' not in kwargs:
raise ValueError("Can't clone and overwrite geometry if the data is not overwritten too.")

for attr in init_args:
if attr not in kwargs:
value = getattr(self, attr)
if attr == 'data' and 'dtype' in kwargs:
value = value.astype(kwargs['dtype'], copy=True)
else:
value = copy.deepcopy(value)

kwargs[attr] = value
return self.__class__(**kwargs)
if 'geom' in kwargs:
raise ValueError("Can't copy and change geometry of the map.")
return self._init_copy(**kwargs)


def __repr__(self):
Expand Down
17 changes: 14 additions & 3 deletions gammapy/maps/geom.py
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,7 @@
from __future__ import absolute_import, division, print_function, unicode_literals
import abc
import copy
import inspect
import re
from collections import OrderedDict
import numpy as np
Expand Down Expand Up @@ -1219,9 +1220,7 @@ def slice_by_idx(self, slices):
axes.append(ax_sliced)
# in the case where isinstance(ax_slice, int) the axes is dropped

kwargs = self._copy_init_kwargs
kwargs['axes'] = axes
return self.__class__(**kwargs)
return self._init_copy(axes=axes)

@abc.abstractmethod
def to_image(self):
Expand Down Expand Up @@ -1418,3 +1417,15 @@ def get_axis_by_type(self, type):
if axis.type == type:
return axis
raise ValueError("Cannot find type {}".format(type))

def _init_copy(self, **kwargs):
"""Init map instance by copying missing init arguments from self.
"""
argnames = inspect.getargspec(self.__init__).args
argnames.remove('self')

for arg in argnames:
value = getattr(self, '_' + arg)
kwargs.setdefault(arg, copy.deepcopy(value))

return self.__class__(**kwargs)
1 change: 1 addition & 0 deletions gammapy/maps/hpx.py
Original file line number Diff line number Diff line change
Expand Up @@ -586,6 +586,7 @@ def __init__(self, nside, nest=True, coordsys='CEL', region=None,
self._coordsys = coordsys
self._maxpix = 12 * self._nside * self._nside
self._maxpix = self._maxpix * np.ones(self._shape, dtype=int)
self._sparse = sparse

self._ipix = None
self._rmap = None
Expand Down
16 changes: 7 additions & 9 deletions gammapy/maps/hpxnd.py
Original file line number Diff line number Diff line change
Expand Up @@ -207,7 +207,7 @@ def sum_over_axes(self):
geom = self.geom.to_image()
axis = tuple(range(self.data.ndim - 1))
data = np.nansum(self.data, axis=axis)
return self.clone(geom=geom, data=data)
return self._init_copy(geom=geom, data=data)

def _reproject_wcs(self, geom, order=1, mode='interp'):

Expand Down Expand Up @@ -250,7 +250,7 @@ def _reproject_hpx(self, geom, order=1, mode='interp'):

def pad(self, pad_width, mode='constant', cval=0.0, order=1):
geom = self.geom.pad(pad_width)
map_out = self.clone(geom=geom, data=None)
map_out = self._init_copy(geom=geom, data=None)
map_out.coadd(self)
coords = geom.get_coord(flat=True)
m = self.geom.contains(coords)
Expand All @@ -271,7 +271,7 @@ def pad(self, pad_width, mode='constant', cval=0.0, order=1):

def crop(self, crop_width):
geom = self.geom.crop(crop_width)
map_out = self.clone(geom=geom, data=None)
map_out = self._init_copy(geom=geom, data=None)
map_out.coadd(self)
return map_out

Expand All @@ -283,16 +283,14 @@ def upsample(self, factor, preserve_counts=True):
if preserve_counts:
data /= factor ** 2

return self.clone(geom=geom, data=data)
return self._init_copy(geom=geom, data=data)

def downsample(self, factor, preserve_counts=True):
geom = self.geom.downsample(factor)
coords = self.geom.get_coord()
vals = self.get_by_coord(coords)

# if we provide data=None the data is not cloned by rather created from
# the altered geometry
map_out = self.clone(geom=geom, data=None)
map_out = self._init_copy(geom=geom, data=None)
map_out.fill_by_coord(coords, vals)

if not preserve_counts:
Expand Down Expand Up @@ -452,7 +450,7 @@ def _make_cols(self, header, conv):
def to_swapped(self):
import healpy as hp
hpx_out = self.geom.to_swapped()
map_out = self.clone(geom=hpx_out, data=None)
map_out = self._init_copy(geom=hpx_out, data=None)
idx = self.geom.get_idx(flat=True)
vals = self.get_by_idx(idx)
if self.geom.nside.size > 1:
Expand All @@ -475,7 +473,7 @@ def to_ud_graded(self, nside, preserve_counts=False):
import healpy as hp
order = nside_to_order(nside)
new_hpx = self.geom.to_ud_graded(order)
map_out = self.clone(geom=new_hpx, data=None)
map_out = self._init_copy(geom=new_hpx, data=None)

if np.all(order <= self.geom.order):
# Downsample
Expand Down
24 changes: 12 additions & 12 deletions gammapy/maps/tests/test_base.py
Original file line number Diff line number Diff line change
Expand Up @@ -45,24 +45,24 @@ def test_map_create(binsz, width, map_type, skydir, axes, unit):

@pytest.mark.parametrize(('binsz', 'width', 'map_type', 'skydir', 'axes', 'unit'),
mapbase_args_with_axes)
def test_map_clone(binsz, width, map_type, skydir, axes, unit):
def test_map_copy(binsz, width, map_type, skydir, axes, unit):
m = Map.create(binsz=binsz, width=width, map_type=map_type,
skydir=skydir, axes=axes, unit=unit)

m_clone = m.clone()
assert repr(m) == repr(m_clone)
m_copy = m.copy()
assert repr(m) == repr(m_copy)

m_clone = m.clone(unit='cm-2 s-1')
assert m_clone.unit == 'cm-2 s-1'
m_copy = m.copy(unit='cm-2 s-1')
assert m_copy.unit == 'cm-2 s-1'
assert m_copy.unit is not m.unit

m_clone = m.clone(meta=OrderedDict([('is_clone', True)]))
assert m_clone.meta['is_clone']
m_copy = m.copy(meta=OrderedDict([('is_copy', True)]))
assert m_copy.meta['is_copy']
assert m_copy.meta is not m.meta

m_clone = m.clone(dtype=np.int)
assert m_clone.data.dtype == np.int

m_clone = m.clone(data=42 * np.ones(m.data.shape))
assert m_clone.data[(0,) * m_clone.data.ndim] == 42
m_copy = m.copy(data=42 * np.ones(m.data.shape))
assert m_copy.data[(0,) * m_copy.data.ndim] == 42
assert m_copy.data is not m.data


def test_map_from_geom():
Expand Down
8 changes: 0 additions & 8 deletions gammapy/maps/wcs.py
Original file line number Diff line number Diff line change
Expand Up @@ -106,14 +106,6 @@ def __init__(self, wcs, npix, cdelt=None, crpix=None, axes=None, conv='gadf'):
self._center_pix[1],
self.wcs)

@property
def _copy_init_kwargs(self):
"""Get kwargs to init an instance with the same parameters."""
kwargs = {}
for arg in ['wcs', 'npix', 'cdelt', 'crpix', 'axes', 'conv']:
kwargs[arg] = getattr(self, '_' + arg)
return kwargs

@property
def wcs(self):
"""WCS projection object."""
Expand Down
Loading

0 comments on commit 49e23a4

Please sign in to comment.