source: trunk/python/scantable.py @ 113

Last change on this file since 113 was 113, checked in by mar637, 20 years ago

version 0.1a

  • Property svn:eol-style set to native
  • Property svn:keywords set to Author Date Id Revision
File size: 13.1 KB
Line 
1from asap._asap import sdtable
2from numarray import ones
3import sys
4
5class scantable(sdtable):
6    """
7        The ASAP container for scans
8    """
9   
10    def __init__(self, filename):
11        """
12        Create a scantable from a saved one or make a reference
13        Parameters:
14            filename:    the name of an asap table on disk, or
15                         [advanced] a refernce to an existing
16                         scantable
17        """
18        self._vb = True
19        self._p = None
20        sdtable.__init__(self, filename)
21
22    def _verbose(self, *args):
23        """
24        Set the verbose level True or False, to indicate if output
25        should be printed as well as returned.
26        """
27        if type(args[0]) is bool:
28            self._vb = args[0]
29            return
30        elif len(args) == 0:
31            return self._vb
32
33
34    def copy(self):
35        """
36        Return a copy of this scantable.
37        Parameters:
38            none
39        Example:
40            copiedscan = scan.copy()
41        """
42        sd = scantable(sdtable._copy(self))
43        return sd
44
45    def get_scan(self, scanid=None):
46        """
47        Return a specific scan (by scanno) or collection of scans (by
48        source name) in a new scantable.
49        Parameters:
50            scanid:    a scanno or a source name
51        Example:
52            scan.get_scan('323p459')
53            # gets all scans containing the source '323p459'
54        """
55        if scanid is None:
56            print "Please specify a scan no or name to retrieve from the scantable"
57        try:
58            if type(scanid) is str:
59                s = sdtable._getsource(self,scanid)
60                return scantable(s)
61            elif type(scanid) is int:
62                s = sdtable._getscan(self,scanid)
63                return scantable(s)
64        except RuntimeError:
65            print "Couldn't find any match."
66
67    def __str__(self):
68        return sdtable.summary(self)
69
70    def summary(self,filename=None):
71        """
72        Print a summary of the contents of this scantable.
73        Parameters:
74            filename:    the name of a file to write the putput to
75                         Default - no file output
76        """
77        info = sdtable.summary(self)
78        if filename is not None:
79            data = open(filename, 'w')
80            data.write(info)
81            data.close()
82        print info
83
84    def set_selection(self, thebeam=0,theif=0,thepol=0):
85        """
86        Set the spectrum for individual operations.
87        Parameters:
88            thebeam,theif,thepol:    a number
89        Example:
90            scan.set_selection(0,0,1)
91            pol1rms = scan.rms(all=False) # returns rms for beam=0
92                                         # if=0, pol=1
93        """
94        self.setbeam(thebeam)
95        self.setpol(thepol)
96        self.setif(theif)
97        return
98
99    def get_selection(self):
100        """
101        Return/print a the current 'cursor' into the Beam/IF/Pol cube.
102        Parameters:
103            none
104        Returns:
105            a list of values (currentBeam,currentIF,currentPol)
106        Example:
107            none
108        """
109        i = self.getbeam()
110        j = self.getif()
111        k = self.getpol()
112        if self._vb:
113            out = 'Beam=%d IF=%d Pol=%d '% (i,j,k)
114            print out
115        return i,j,k
116
117    def rms(self,mask=None, all=True):
118        """
119        Determine the root mean square of the current beam/if/pol
120        Takes a 'mask' as an optional parameter to specify which
121        channels should be excluded.
122        Parameters:
123            mask:    an optional mask specifying where the rms
124                     should be determined.
125            all:     optional flag to show all or a selected
126                     spectrum of Beam/IF/Pol
127
128        Example:
129            scan.set_unit('channel')
130            msk = scan.create_mask([100,200],[500,600])
131            scan.rms(mask=m)
132        """
133        from asap._asap import rms as _rms
134        if mask == None:
135            mask = ones(self.nchan())
136        if all:
137            out = ''
138            tmp = []
139            for i in range(self.nbeam()):
140                self.setbeam(i)
141                for j in range(self.nif()):
142                    self.setif(j)
143                    for k in range(self.npol()):
144                        self.setpol(k)
145                        rmsval = _rms(self,mask)
146                        tmp.append(rmsval)
147                        out += 'Beam[%d], IF[%d], Pol[%d] = %3.3f\n' % (i,j,k,rmsval)
148            if self._vb:
149                print out
150            return tmp
151
152        else:
153            i = self.getbeam()
154            j = self.getif()
155            k = self.getpol()
156            rmsval = _rms(self,mask)
157            out = 'Beam[%d], IF[%d], Pol[%d] = %3.3f' % (i,j,k,rmsval)
158            if self._vb:
159                print out
160            return rmsval
161
162    def get_tsys(self, all=True):
163        """
164        Return the System temperatures.
165        Parameters:
166            all:    optional parameter to get the Tsys values for all
167                    Beams/IFs/Pols (default) or just the one selected
168                    with scantable.set_selection()
169                    [True or False]
170        Returns:
171            a list of Tsys values.
172        """
173        if all:
174            tmp = []
175            out = ''
176            for i in range(self.nbeam()):
177                self.setbeam(i)
178                for j in range(self.nif()):
179                    self.setif(j)
180                    for k in range(self.npol()):
181                        self.setpol(k)
182                        ts = self._gettsys()
183                        tmp.append(ts)
184                        out += 'TSys: Beam[%d], IF[%d], Pol[%d] = %3.3f\n' % (i,j,k,ts)
185            if self._vb:
186                print out
187            return tmp
188        else:
189            i = self.getbeam()
190            j = self.getif()
191            k = self.getpol()
192            ts = self._gettsys()
193            out = 'TSys: Beam[%d], IF[%d], Pol[%d] = %3.3f' % (i,j,k,ts)
194            if self._vb:
195                print out
196            return ts
197       
198    def get_time(self):
199        """
200        Get a list of time stamps for the observations.
201        Return a string for each intergration in the scantable.
202        Parameters:
203            none
204        Example:
205            none
206        """
207        out = []
208        for i in range(self.nrow()):
209            out.append(self._gettime(i))
210        return out
211
212    def set_unit(self, unit='channel'):
213        """
214        Set the unit for all following operations on this scantable
215        Parameters:
216            unit:    optional unit, default is 'channel'
217                     one of '*Hz','km/s','channel', ''
218        """
219
220        if unit in ['','pixel', 'channel']:
221            unit = ''
222        inf = list(self._getcoordinfo())
223        inf[0] = unit
224        self._setcoordinfo(inf)
225        if self._p: self.plot()
226
227    def set_freqframe(self, frame='LSRK'):
228        """
229        Set the frame type of the Spectral Axis.
230        Parameters:
231            frame:   an optional frame type, default 'LSRK'.
232        Examples:
233            scan.set_freqframe('BARY')
234        """
235        valid = ['REST','TOPO','LSRD','LSRK','BARY', \
236                   'GEO','GALACTO','LGROUP','CMB']
237        if frame in valid:
238            inf = list(self._getcoordinfo())
239            inf[1] = frame
240            self._setcoordinfo(inf)
241        else:
242            print "Please specify a valid freq type. Valid types are:\n",valid
243           
244    def get_unit(self):
245        """
246        Get the default unit set in this scantable
247        Parameters:
248        Returns:
249            A unit string
250        """
251        inf = self._getcoordinfo()
252        unit = inf[0]
253        if unit == '': unit = 'channel'
254        return unit
255
256    def get_abscissa(self, rowno=0):
257        """
258        Get the abscissa in the current coordinate setup for the currently
259        selected Beam/IF/Pol
260        Parameters:
261            none
262        Returns:
263            The abscissa values and it's format string.
264        """
265        absc = self.getabscissa(rowno)
266        lbl = self.getabscissalabel(rowno)
267        return absc, lbl
268
269    def create_mask(self, *args, **kwargs):
270        """
271        Compute and return a mask based on [min,max] windows.
272        The specified windows are to be EXCLUDED, when the mask is
273        applied.
274        Parameters:
275            [min,max],[min2,max2],...
276                Pairs of start/end points specifying the regions
277                to be masked
278            invert:     return an inverted mask, i.e. the regions
279                        specified are not masked (INCLUDED)
280        Example:
281            scan.set_unit('channel')
282
283            a)
284            msk = scan.set_mask([400,500],[800,900])
285            # masks the regions between 400 and 500
286            # and 800 and 900 in the unit 'channel'
287
288            b)
289            msk = scan.set_mask([400,500],[800,900], invert=True)
290            # masks the regions outside 400 and 500
291            # and 800 and 900 in the unit 'channel'
292           
293        """
294        u = self._getcoordinfo()[0]
295        if self._vb:
296            if u == "": u = "channel"
297            print "The current mask window unit is", u
298        n = self.nchan()
299        data = self.getabscissa()
300        msk = ones(n)
301        for  window in args:
302            if (len(window) != 2 or window[0] > window[1] ):
303                print "A window needs to be defined as [min,max]"
304                return
305            for i in range(n):
306                if data[i] >= window[0] and data[i] < window[1]:
307                    msk[i] = 0
308        if kwargs.has_key('invert'):
309            if kwargs.get('invert'):
310                from numarray import logical_not
311                msk = logical_not(msk)
312        return msk
313   
314    def set_restfreqs(self, freqs, unit='Hz'):
315        """
316        Set the restfrequency(s) for this scantable.
317        Parameters:
318            freqs:    one or more frequencies
319            unit:     optional 'unit', default 'Hz'
320        Example:
321            scan.set_restfreqs([1000000000.0])
322        """
323        if type(freqs) is float or int:
324            freqs = (freqs)
325        sdtable._setrestfreqs(self,freqs, unit)
326        return
327
328    def flag_spectrum(self, thebeam, theif, thepol):
329        """
330        This flags a selected spectrum in the scan 'for good'.
331        USE WITH CARE - not reversible.
332        Use masks for non-permanent exclusion of channels.
333        Parameters:
334            thebeam,theif,thepol:    all have to be explicitly
335                                     specified
336        Example:
337            scan.flag_spectrum(0,0,1)
338            flags the spectrum for Beam=0, IF=0, Pol=1
339        """
340        if (thebeam < self.nbeam() and  theif < self.nif() and thepol < self.npol()):
341            stable.setbeam(thebeam)
342            stable.setif(theif)
343            stable.setpol(thepol)
344            stable._flag(self)
345        else:
346            print "Please specify a valid (Beam/IF/Pol)"
347        return
348
349    def plot(self, what='spectrum',col='Pol', panel=None):
350        """
351        Plot the spectra contained in the scan. Alternatively you can also
352        Plot Tsys vs Time
353        Parameters:
354            what:     a choice of 'spectrum' (default) or 'tsys'
355            col:      which out of Beams/IFs/Pols should be colour stacked
356            panel:    set up multiple panels, currently not working.
357        """
358        validcol = {'Beam':self.nbeam(),'IF':self.nif(),'Pol':self.npol()}
359        validyax = ['spectrum','tsys']
360        if not self._p:
361            from asap.asaplot import ASAPlot
362            self._p = ASAPlot()
363#            print "Plotting not enabled"
364#            return
365        npan = 1
366        x = None
367        if what == 'tsys':
368            n = self.nrow()
369            if n < 2:
370                print "Only one integration. Can't plot."
371                return
372        if panel == 'Time':
373            npan = self.nrow()
374        self._p.hold()
375        self._p.clear()
376        xlab,ylab,tlab = None,None,None
377        vb = self._verbose
378        self._verbose(False)
379        sel = self.get_selection()
380        for i in range(npan):
381            for j in range(validcol[col]):
382                x = None
383                y = None
384                m = None
385                tlab = self._getsourcename(i)
386                if col == 'Beam':
387                    self.setbeam(j)
388                elif col == 'IF':
389                    self.setif(j)
390                elif col == 'Pol':
391                    self.setpol(j)
392                if what == 'tsys':
393                    x = range(self.nrow())
394                    xlab = 'Time [pixel]'
395                    m = list(ones(len(x)))
396                    y = []
397                    ylab = r'$T_{sys}$'
398                    for k in range(len(x)):
399                        y.append(self._gettsys(k))
400                else:
401                    x,xlab = self.get_abscissa(i)
402                    y = self.getspectrum(i)
403                    ylab = r'Flux'
404                    m = self.getmask(i)
405                llab = col+' '+str(j)
406                self._p.set_line(label=llab)
407                self._p.plot(x,y,m)
408        self._p.set_axes('xlabel',xlab)
409        self._p.set_axes('ylabel',ylab)
410        self._p.set_axes('title',tlab)
411        self._p.release()
412        self.set_selection(sel[0],sel[1],sel[2])
413        self._verbose(vb)
414        return
Note: See TracBrowser for help on using the repository browser.