##// END OF EJS Templates
Bug fixed: Error decoding data
Miguel Valdez -
r678:929f201d0968
parent child
Show More
@@ -1,1095 +1,1091
1 1 import numpy
2 2
3 3 from jroproc_base import ProcessingUnit, Operation
4 4 from schainpy.model.data.jrodata import Voltage
5 5
6 6 class VoltageProc(ProcessingUnit):
7 7
8 8
9 9 def __init__(self):
10 10
11 11 ProcessingUnit.__init__(self)
12 12
13 13 # self.objectDict = {}
14 14 self.dataOut = Voltage()
15 15 self.flip = 1
16 16
17 17 def run(self):
18 18 if self.dataIn.type == 'AMISR':
19 19 self.__updateObjFromAmisrInput()
20 20
21 21 if self.dataIn.type == 'Voltage':
22 22 self.dataOut.copy(self.dataIn)
23 23
24 24 # self.dataOut.copy(self.dataIn)
25 25
26 26 def __updateObjFromAmisrInput(self):
27 27
28 28 self.dataOut.timeZone = self.dataIn.timeZone
29 29 self.dataOut.dstFlag = self.dataIn.dstFlag
30 30 self.dataOut.errorCount = self.dataIn.errorCount
31 31 self.dataOut.useLocalTime = self.dataIn.useLocalTime
32 32
33 33 self.dataOut.flagNoData = self.dataIn.flagNoData
34 34 self.dataOut.data = self.dataIn.data
35 35 self.dataOut.utctime = self.dataIn.utctime
36 36 self.dataOut.channelList = self.dataIn.channelList
37 37 # self.dataOut.timeInterval = self.dataIn.timeInterval
38 38 self.dataOut.heightList = self.dataIn.heightList
39 39 self.dataOut.nProfiles = self.dataIn.nProfiles
40 40
41 41 self.dataOut.nCohInt = self.dataIn.nCohInt
42 42 self.dataOut.ippSeconds = self.dataIn.ippSeconds
43 43 self.dataOut.frequency = self.dataIn.frequency
44 44
45 45 self.dataOut.azimuth = self.dataIn.azimuth
46 46 self.dataOut.zenith = self.dataIn.zenith
47 47
48 48 self.dataOut.beam.codeList = self.dataIn.beam.codeList
49 49 self.dataOut.beam.azimuthList = self.dataIn.beam.azimuthList
50 50 self.dataOut.beam.zenithList = self.dataIn.beam.zenithList
51 51 #
52 52 # pass#
53 53 #
54 54 # def init(self):
55 55 #
56 56 #
57 57 # if self.dataIn.type == 'AMISR':
58 58 # self.__updateObjFromAmisrInput()
59 59 #
60 60 # if self.dataIn.type == 'Voltage':
61 61 # self.dataOut.copy(self.dataIn)
62 62 # # No necesita copiar en cada init() los atributos de dataIn
63 63 # # la copia deberia hacerse por cada nuevo bloque de datos
64 64
65 65 def selectChannels(self, channelList):
66 66
67 67 channelIndexList = []
68 68
69 69 for channel in channelList:
70 70 if channel not in self.dataOut.channelList:
71 71 raise ValueError, "Channel %d is not in %s" %(channel, str(self.dataOut.channelList))
72 72
73 73 index = self.dataOut.channelList.index(channel)
74 74 channelIndexList.append(index)
75 75
76 76 self.selectChannelsByIndex(channelIndexList)
77 77
78 78 def selectChannelsByIndex(self, channelIndexList):
79 79 """
80 80 Selecciona un bloque de datos en base a canales segun el channelIndexList
81 81
82 82 Input:
83 83 channelIndexList : lista sencilla de canales a seleccionar por ej. [2,3,7]
84 84
85 85 Affected:
86 86 self.dataOut.data
87 87 self.dataOut.channelIndexList
88 88 self.dataOut.nChannels
89 89 self.dataOut.m_ProcessingHeader.totalSpectra
90 90 self.dataOut.systemHeaderObj.numChannels
91 91 self.dataOut.m_ProcessingHeader.blockSize
92 92
93 93 Return:
94 94 None
95 95 """
96 96
97 97 for channelIndex in channelIndexList:
98 98 if channelIndex not in self.dataOut.channelIndexList:
99 99 print channelIndexList
100 100 raise ValueError, "The value %d in channelIndexList is not valid" %channelIndex
101 101
102 102 # nChannels = len(channelIndexList)
103 103 if self.dataOut.flagDataAsBlock:
104 104 """
105 105 Si la data es obtenida por bloques, dimension = [nChannels, nProfiles, nHeis]
106 106 """
107 107 data = self.dataOut.data[channelIndexList,:,:]
108 108 else:
109 109 data = self.dataOut.data[channelIndexList,:]
110 110
111 111 self.dataOut.data = data
112 112 self.dataOut.channelList = [self.dataOut.channelList[i] for i in channelIndexList]
113 113 # self.dataOut.nChannels = nChannels
114 114
115 115 return 1
116 116
117 117 def selectHeights(self, minHei=None, maxHei=None):
118 118 """
119 119 Selecciona un bloque de datos en base a un grupo de valores de alturas segun el rango
120 120 minHei <= height <= maxHei
121 121
122 122 Input:
123 123 minHei : valor minimo de altura a considerar
124 124 maxHei : valor maximo de altura a considerar
125 125
126 126 Affected:
127 127 Indirectamente son cambiados varios valores a travez del metodo selectHeightsByIndex
128 128
129 129 Return:
130 130 1 si el metodo se ejecuto con exito caso contrario devuelve 0
131 131 """
132 132
133 133 if minHei == None:
134 134 minHei = self.dataOut.heightList[0]
135 135
136 136 if maxHei == None:
137 137 maxHei = self.dataOut.heightList[-1]
138 138
139 139 if (minHei < self.dataOut.heightList[0]):
140 140 minHei = self.dataOut.heightList[0]
141 141 # raise ValueError, "height range [%d,%d] is not valid. Data height range is [%d, %d]" % (minHei,
142 142 # maxHei,
143 143 # self.dataOut.heightList[0],
144 144 # self.dataOut.heightList[-1])
145 145
146 146 if (maxHei > self.dataOut.heightList[-1]):
147 147 maxHei = self.dataOut.heightList[-1]
148 148 # raise ValueError, "some value in (%d,%d) is not valid" % (minHei, maxHei)
149 149
150 150 minIndex = 0
151 151 maxIndex = 0
152 152 heights = self.dataOut.heightList
153 153
154 154 inda = numpy.where(heights >= minHei)
155 155 indb = numpy.where(heights <= maxHei)
156 156
157 157 try:
158 158 minIndex = inda[0][0]
159 159 except:
160 160 minIndex = 0
161 161
162 162 try:
163 163 maxIndex = indb[0][-1]
164 164 except:
165 165 maxIndex = len(heights)
166 166
167 167 self.selectHeightsByIndex(minIndex, maxIndex)
168 168
169 169 return 1
170 170
171 171
172 172 def selectHeightsByIndex(self, minIndex, maxIndex):
173 173 """
174 174 Selecciona un bloque de datos en base a un grupo indices de alturas segun el rango
175 175 minIndex <= index <= maxIndex
176 176
177 177 Input:
178 178 minIndex : valor de indice minimo de altura a considerar
179 179 maxIndex : valor de indice maximo de altura a considerar
180 180
181 181 Affected:
182 182 self.dataOut.data
183 183 self.dataOut.heightList
184 184
185 185 Return:
186 186 1 si el metodo se ejecuto con exito caso contrario devuelve 0
187 187 """
188 188
189 189 if (minIndex < 0) or (minIndex > maxIndex):
190 190 raise ValueError, "some value in (%d,%d) is not valid" % (minIndex, maxIndex)
191 191
192 192 if (maxIndex >= self.dataOut.nHeights):
193 193 maxIndex = self.dataOut.nHeights
194 194 # raise ValueError, "some value in (%d,%d) is not valid" % (minIndex, maxIndex)
195 195
196 196 # nHeights = maxIndex - minIndex + 1
197 197
198 198 #voltage
199 199 if self.dataOut.flagDataAsBlock:
200 200 """
201 201 Si la data es obtenida por bloques, dimension = [nChannels, nProfiles, nHeis]
202 202 """
203 203 data = self.dataOut.data[:,:, minIndex:maxIndex]
204 204 else:
205 205 data = self.dataOut.data[:, minIndex:maxIndex]
206 206
207 207 # firstHeight = self.dataOut.heightList[minIndex]
208 208
209 209 self.dataOut.data = data
210 210 self.dataOut.heightList = self.dataOut.heightList[minIndex:maxIndex]
211 211
212 212 if self.dataOut.nHeights <= 1:
213 213 raise ValueError, "selectHeights: Too few heights. Current number of heights is %d" %(self.dataOut.nHeights)
214 214
215 215 return 1
216 216
217 217
218 218 def filterByHeights(self, window):
219 219
220 220 deltaHeight = self.dataOut.heightList[1] - self.dataOut.heightList[0]
221 221
222 222 if window == None:
223 223 window = (self.dataOut.radarControllerHeaderObj.txA/self.dataOut.radarControllerHeaderObj.nBaud) / deltaHeight
224 224
225 225 newdelta = deltaHeight * window
226 226 r = self.dataOut.nHeights % window
227 227 newheights = (self.dataOut.nHeights-r)/window
228 228
229 229 if newheights <= 1:
230 230 raise ValueError, "filterByHeights: Too few heights. Current number of heights is %d and window is %d" %(self.dataOut.nHeights, window)
231 231
232 232 if self.dataOut.flagDataAsBlock:
233 233 """
234 234 Si la data es obtenida por bloques, dimension = [nChannels, nProfiles, nHeis]
235 235 """
236 236 buffer = self.dataOut.data[:, :, 0:self.dataOut.nHeights-r]
237 237 buffer = buffer.reshape(self.dataOut.nChannels,self.dataOut.nProfiles,self.dataOut.nHeights/window,window)
238 238 buffer = numpy.sum(buffer,3)
239 239
240 240 else:
241 241 buffer = self.dataOut.data[:,0:self.dataOut.nHeights-r]
242 242 buffer = buffer.reshape(self.dataOut.nChannels,self.dataOut.nHeights/window,window)
243 243 buffer = numpy.sum(buffer,2)
244 244
245 245 self.dataOut.data = buffer
246 246 self.dataOut.heightList = self.dataOut.heightList[0] + numpy.arange( newheights )*newdelta
247 247 self.dataOut.windowOfFilter = window
248 248
249 249 def setH0(self, h0, deltaHeight = None):
250 250
251 251 if not deltaHeight:
252 252 deltaHeight = self.dataOut.heightList[1] - self.dataOut.heightList[0]
253 253
254 254 nHeights = self.dataOut.nHeights
255 255
256 256 newHeiRange = h0 + numpy.arange(nHeights)*deltaHeight
257 257
258 258 self.dataOut.heightList = newHeiRange
259 259
260 260 def deFlip(self, channelList = []):
261 261
262 262 data = self.dataOut.data.copy()
263 263
264 264 if self.dataOut.flagDataAsBlock:
265 265 flip = self.flip
266 266 profileList = range(self.dataOut.nProfiles)
267 267
268 268 if not channelList:
269 269 for thisProfile in profileList:
270 270 data[:,thisProfile,:] = data[:,thisProfile,:]*flip
271 271 flip *= -1.0
272 272 else:
273 273 for thisChannel in channelList:
274 274 if thisChannel not in self.dataOut.channelList:
275 275 continue
276 276
277 277 for thisProfile in profileList:
278 278 data[thisChannel,thisProfile,:] = data[thisChannel,thisProfile,:]*flip
279 279 flip *= -1.0
280 280
281 281 self.flip = flip
282 282
283 283 else:
284 284 if not channelList:
285 285 data[:,:] = data[:,:]*self.flip
286 286 else:
287 287 for thisChannel in channelList:
288 288 if thisChannel not in self.dataOut.channelList:
289 289 continue
290 290
291 291 data[thisChannel,:] = data[thisChannel,:]*self.flip
292 292
293 293 self.flip *= -1.
294 294
295 295 self.dataOut.data = data
296 296
297 297 def setRadarFrequency(self, frequency=None):
298 298
299 299 if frequency != None:
300 300 self.dataOut.frequency = frequency
301 301
302 302 return 1
303 303
304 304 class CohInt(Operation):
305 305
306 306 isConfig = False
307 307
308 308 __profIndex = 0
309 309 __withOverapping = False
310 310
311 311 __byTime = False
312 312 __initime = None
313 313 __lastdatatime = None
314 314 __integrationtime = None
315 315
316 316 __buffer = None
317 317
318 318 __dataReady = False
319 319
320 320 n = None
321 321
322 322
323 323 def __init__(self):
324 324
325 325 Operation.__init__(self)
326 326
327 327 # self.isConfig = False
328 328
329 329 def setup(self, n=None, timeInterval=None, overlapping=False, byblock=False):
330 330 """
331 331 Set the parameters of the integration class.
332 332
333 333 Inputs:
334 334
335 335 n : Number of coherent integrations
336 336 timeInterval : Time of integration. If the parameter "n" is selected this one does not work
337 337 overlapping :
338 338
339 339 """
340 340
341 341 self.__initime = None
342 342 self.__lastdatatime = 0
343 343 self.__buffer = None
344 344 self.__dataReady = False
345 345 self.byblock = byblock
346 346
347 347 if n == None and timeInterval == None:
348 348 raise ValueError, "n or timeInterval should be specified ..."
349 349
350 350 if n != None:
351 351 self.n = n
352 352 self.__byTime = False
353 353 else:
354 354 self.__integrationtime = timeInterval #* 60. #if (type(timeInterval)!=integer) -> change this line
355 355 self.n = 9999
356 356 self.__byTime = True
357 357
358 358 if overlapping:
359 359 self.__withOverapping = True
360 360 self.__buffer = None
361 361 else:
362 362 self.__withOverapping = False
363 363 self.__buffer = 0
364 364
365 365 self.__profIndex = 0
366 366
367 367 def putData(self, data):
368 368
369 369 """
370 370 Add a profile to the __buffer and increase in one the __profileIndex
371 371
372 372 """
373 373
374 374 if not self.__withOverapping:
375 375 self.__buffer += data.copy()
376 376 self.__profIndex += 1
377 377 return
378 378
379 379 #Overlapping data
380 380 nChannels, nHeis = data.shape
381 381 data = numpy.reshape(data, (1, nChannels, nHeis))
382 382
383 383 #If the buffer is empty then it takes the data value
384 384 if self.__buffer is None:
385 385 self.__buffer = data
386 386 self.__profIndex += 1
387 387 return
388 388
389 389 #If the buffer length is lower than n then stakcing the data value
390 390 if self.__profIndex < self.n:
391 391 self.__buffer = numpy.vstack((self.__buffer, data))
392 392 self.__profIndex += 1
393 393 return
394 394
395 395 #If the buffer length is equal to n then replacing the last buffer value with the data value
396 396 self.__buffer = numpy.roll(self.__buffer, -1, axis=0)
397 397 self.__buffer[self.n-1] = data
398 398 self.__profIndex = self.n
399 399 return
400 400
401 401
402 402 def pushData(self):
403 403 """
404 404 Return the sum of the last profiles and the profiles used in the sum.
405 405
406 406 Affected:
407 407
408 408 self.__profileIndex
409 409
410 410 """
411 411
412 412 if not self.__withOverapping:
413 413 data = self.__buffer
414 414 n = self.__profIndex
415 415
416 416 self.__buffer = 0
417 417 self.__profIndex = 0
418 418
419 419 return data, n
420 420
421 421 #Integration with Overlapping
422 422 data = numpy.sum(self.__buffer, axis=0)
423 423 n = self.__profIndex
424 424
425 425 return data, n
426 426
427 427 def byProfiles(self, data):
428 428
429 429 self.__dataReady = False
430 430 avgdata = None
431 431 # n = None
432 432
433 433 self.putData(data)
434 434
435 435 if self.__profIndex == self.n:
436 436
437 437 avgdata, n = self.pushData()
438 438 self.__dataReady = True
439 439
440 440 return avgdata
441 441
442 442 def byTime(self, data, datatime):
443 443
444 444 self.__dataReady = False
445 445 avgdata = None
446 446 n = None
447 447
448 448 self.putData(data)
449 449
450 450 if (datatime - self.__initime) >= self.__integrationtime:
451 451 avgdata, n = self.pushData()
452 452 self.n = n
453 453 self.__dataReady = True
454 454
455 455 return avgdata
456 456
457 457 def integrate(self, data, datatime=None):
458 458
459 459 if self.__initime == None:
460 460 self.__initime = datatime
461 461
462 462 if self.__byTime:
463 463 avgdata = self.byTime(data, datatime)
464 464 else:
465 465 avgdata = self.byProfiles(data)
466 466
467 467
468 468 self.__lastdatatime = datatime
469 469
470 470 if avgdata is None:
471 471 return None, None
472 472
473 473 avgdatatime = self.__initime
474 474
475 475 deltatime = datatime -self.__lastdatatime
476 476
477 477 if not self.__withOverapping:
478 478 self.__initime = datatime
479 479 else:
480 480 self.__initime += deltatime
481 481
482 482 return avgdata, avgdatatime
483 483
484 484 def integrateByBlock(self, dataOut):
485 485
486 486 times = int(dataOut.data.shape[1]/self.n)
487 487 avgdata = numpy.zeros((dataOut.nChannels, times, dataOut.nHeights), dtype=numpy.complex)
488 488
489 489 id_min = 0
490 490 id_max = self.n
491 491
492 492 for i in range(times):
493 493 junk = dataOut.data[:,id_min:id_max,:]
494 494 avgdata[:,i,:] = junk.sum(axis=1)
495 495 id_min += self.n
496 496 id_max += self.n
497 497
498 498 timeInterval = dataOut.ippSeconds*self.n
499 499 avgdatatime = (times - 1) * timeInterval + dataOut.utctime
500 500 self.__dataReady = True
501 501 return avgdata, avgdatatime
502 502
503 503 def run(self, dataOut, **kwargs):
504 504
505 505 if not self.isConfig:
506 506 self.setup(**kwargs)
507 507 self.isConfig = True
508 508
509 509 if dataOut.flagDataAsBlock:
510 510 """
511 511 Si la data es leida por bloques, dimension = [nChannels, nProfiles, nHeis]
512 512 """
513 513 avgdata, avgdatatime = self.integrateByBlock(dataOut)
514 514 else:
515 515 avgdata, avgdatatime = self.integrate(dataOut.data, dataOut.utctime)
516 516
517 517 # dataOut.timeInterval *= n
518 518 dataOut.flagNoData = True
519 519
520 520 if self.__dataReady:
521 521 dataOut.data = avgdata
522 522 dataOut.nCohInt *= self.n
523 523 dataOut.utctime = avgdatatime
524 524 # dataOut.timeInterval = dataOut.ippSeconds * dataOut.nCohInt
525 525 dataOut.flagNoData = False
526 526
527 527 class Decoder(Operation):
528 528
529 529 isConfig = False
530 530 __profIndex = 0
531 531
532 532 code = None
533 533
534 534 nCode = None
535 535 nBaud = None
536 536
537 537
538 538 def __init__(self):
539 539
540 540 Operation.__init__(self)
541 541
542 542 self.times = None
543 543 self.osamp = None
544 544 # self.__setValues = False
545 545 self.isConfig = False
546 546
547 547 def setup(self, code, osamp, dataOut):
548 548
549 549 self.__profIndex = 0
550 550
551 551 self.code = code
552 552
553 553 self.nCode = len(code)
554 554 self.nBaud = len(code[0])
555 555
556 556 if (osamp != None) and (osamp >1):
557 557 self.osamp = osamp
558 558 self.code = numpy.repeat(code, repeats=self.osamp, axis=1)
559 559 self.nBaud = self.nBaud*self.osamp
560 560
561 561 self.__nChannels = dataOut.nChannels
562 562 self.__nProfiles = dataOut.nProfiles
563 563 self.__nHeis = dataOut.nHeights
564 564
565 565 if self.__nHeis < self.nBaud:
566 566 print 'IOError: Number of heights (%d) should be greater than number of bauds (%d)' %(self.__nHeis, self.nBaud)
567 567 raise IOError, 'Number of heights (%d) should be greater than number of bauds (%d)' %(self.__nHeis, self.nBaud)
568 568
569 569 #Frequency
570 570 __codeBuffer = numpy.zeros((self.nCode, self.__nHeis), dtype=numpy.complex)
571 571
572 572 __codeBuffer[:,0:self.nBaud] = self.code
573 573
574 574 self.fft_code = numpy.conj(numpy.fft.fft(__codeBuffer, axis=1))
575 575
576 576 if dataOut.flagDataAsBlock:
577 577
578 578 self.ndatadec = self.__nHeis #- self.nBaud + 1
579 579
580 580 self.datadecTime = numpy.zeros((self.__nChannels, self.__nProfiles, self.ndatadec), dtype=numpy.complex)
581 581
582 582 else:
583 583
584 584 #Time
585 585 self.ndatadec = self.__nHeis #- self.nBaud + 1
586 586
587 587 self.datadecTime = numpy.zeros((self.__nChannels, self.ndatadec), dtype=numpy.complex)
588 588
589 589 def __convolutionInFreq(self, data):
590 590
591 591 fft_code = self.fft_code[self.__profIndex].reshape(1,-1)
592 592
593 593 fft_data = numpy.fft.fft(data, axis=1)
594 594
595 595 conv = fft_data*fft_code
596 596
597 597 data = numpy.fft.ifft(conv,axis=1)
598 598
599 599 return data
600 600
601 601 def __convolutionInFreqOpt(self, data):
602 602
603 603 raise NotImplementedError
604 604
605 605 # fft_code = self.fft_code[self.__profIndex].reshape(1,-1)
606 606 #
607 607 # data = cfunctions.decoder(fft_code, data)
608 608 #
609 609 # datadec = data#[:,:]
610 610 #
611 611 # return datadec
612 612
613 613 def __convolutionInTime(self, data):
614 614
615 615 code = self.code[self.__profIndex]
616 616
617 617 for i in range(self.__nChannels):
618 618 self.datadecTime[i,:] = numpy.correlate(data[i,:], code, mode='full')[self.nBaud-1:]
619 619
620 620 return self.datadecTime
621 621
622 622 def __convolutionByBlockInTime(self, data):
623 623
624 624 repetitions = self.__nProfiles / self.nCode
625 625
626 626 junk = numpy.lib.stride_tricks.as_strided(self.code, (repetitions, self.code.size), (0, self.code.itemsize))
627 627 junk = junk.flatten()
628 628 code_block = numpy.reshape(junk, (self.nCode*repetitions, self.nBaud))
629 629
630 630 for i in range(self.__nChannels):
631 631 for j in range(self.__nProfiles):
632 632 self.datadecTime[i,j,:] = numpy.correlate(data[i,j,:], code_block[j,:], mode='full')[self.nBaud-1:]
633 633
634 634 return self.datadecTime
635 635
636 636 def __convolutionByBlockInFreq(self, data):
637 637
638 638 fft_code = self.fft_code[self.__profIndex].reshape(1,-1)
639 639
640 640 fft_data = numpy.fft.fft(data, axis=2)
641 641
642 642 conv = fft_data*fft_code
643 643
644 644 data = numpy.fft.ifft(conv,axis=2)
645 645
646 646 return data
647 647
648 648 def run(self, dataOut, code=None, nCode=None, nBaud=None, mode = 0, osamp=None, times=None):
649 649
650 dataOut.flagNoData = True
651
652 650 if dataOut.flagDecodeData:
653 651 print "This data is already decoded, recoding again ..."
654 652
655 653 if not self.isConfig:
656 654
657 655 if code is None:
658 656 if dataOut.code is None:
659 657 print "Code is not defined"
660 658 raise ValueError, "Code could not be read from %s object. Enter a value in Code parameter" %dataOut.type
661 659
662 660 code = dataOut.code
663 661 else:
664 662 code = numpy.array(code).reshape(nCode,nBaud)
665 663
666 664 self.setup(code, osamp, dataOut)
667 665
668 666 self.isConfig = True
669 667
670 668 if self.code is None:
671 669 print "Fail decoding: Code is not defined."
672 670 return
673 671
674 672 datadec = None
675 673
676 674 if dataOut.flagDataAsBlock:
677 675 """
678 676 Decoding when data have been read as block,
679 677 """
680 678 if mode == 0:
681 679 datadec = self.__convolutionByBlockInTime(dataOut.data)
682 680 if mode == 1:
683 681 datadec = self.__convolutionByBlockInFreq(dataOut.data)
684 682 else:
685 683 """
686 684 Decoding when data have been read profile by profile
687 685 """
688 686 if mode == 0:
689 687 datadec = self.__convolutionInTime(dataOut.data)
690 688
691 689 if mode == 1:
692 690 datadec = self.__convolutionInFreq(dataOut.data)
693 691
694 692 if mode == 2:
695 693 datadec = self.__convolutionInFreqOpt(dataOut.data)
696 694
697 695 if datadec is None:
698 696 raise ValueError, "Codification mode selected is not valid: mode=%d. Try selecting 0 or 1" %mode
699 697
700 698 dataOut.code = self.code
701 699 dataOut.nCode = self.nCode
702 700 dataOut.nBaud = self.nBaud
703 701
704 702 dataOut.data = datadec
705 703
706 704 dataOut.heightList = dataOut.heightList[0:datadec.shape[-1]]
707 705
708 706 dataOut.flagDecodeData = True #asumo q la data esta decodificada
709 707
710 708 if self.__profIndex == self.nCode-1:
711 709 self.__profIndex = 0
712 710 return 1
713 711
714 712 self.__profIndex += 1
715 713
716 dataOut.flagNoData = False
717
718 714 return 1
719 715 # dataOut.flagDeflipData = True #asumo q la data no esta sin flip
720 716
721 717
722 718 class ProfileConcat(Operation):
723 719
724 720 isConfig = False
725 721 buffer = None
726 722
727 723 def __init__(self):
728 724
729 725 Operation.__init__(self)
730 726 self.profileIndex = 0
731 727
732 728 def reset(self):
733 729 self.buffer = numpy.zeros_like(self.buffer)
734 730 self.start_index = 0
735 731 self.times = 1
736 732
737 733 def setup(self, data, m, n=1):
738 734 self.buffer = numpy.zeros((data.shape[0],data.shape[1]*m),dtype=type(data[0,0]))
739 735 self.nHeights = data.nHeights
740 736 self.start_index = 0
741 737 self.times = 1
742 738
743 739 def concat(self, data):
744 740
745 741 self.buffer[:,self.start_index:self.profiles*self.times] = data.copy()
746 742 self.start_index = self.start_index + self.nHeights
747 743
748 744 def run(self, dataOut, m):
749 745
750 746 dataOut.flagNoData = True
751 747
752 748 if not self.isConfig:
753 749 self.setup(dataOut.data, m, 1)
754 750 self.isConfig = True
755 751
756 752 if dataOut.flagDataAsBlock:
757 753
758 754 raise ValueError, "ProfileConcat can only be used when voltage have been read profile by profile, getBlock = False"
759 755
760 756 else:
761 757 self.concat(dataOut.data)
762 758 self.times += 1
763 759 if self.times > m:
764 760 dataOut.data = self.buffer
765 761 self.reset()
766 762 dataOut.flagNoData = False
767 763 # se deben actualizar mas propiedades del header y del objeto dataOut, por ejemplo, las alturas
768 764 deltaHeight = dataOut.heightList[1] - dataOut.heightList[0]
769 765 xf = dataOut.heightList[0] + dataOut.nHeights * deltaHeight * m
770 766 dataOut.heightList = numpy.arange(dataOut.heightList[0], xf, deltaHeight)
771 767 dataOut.ippSeconds *= m
772 768
773 769 class ProfileSelector(Operation):
774 770
775 771 profileIndex = None
776 772 # Tamanho total de los perfiles
777 773 nProfiles = None
778 774
779 775 def __init__(self):
780 776
781 777 Operation.__init__(self)
782 778 self.profileIndex = 0
783 779
784 780 def incIndex(self):
785 781
786 782 self.profileIndex += 1
787 783
788 784 if self.profileIndex >= self.nProfiles:
789 785 self.profileIndex = 0
790 786
791 787 def isThisProfileInRange(self, profileIndex, minIndex, maxIndex):
792 788
793 789 if profileIndex < minIndex:
794 790 return False
795 791
796 792 if profileIndex > maxIndex:
797 793 return False
798 794
799 795 return True
800 796
801 797 def isThisProfileInList(self, profileIndex, profileList):
802 798
803 799 if profileIndex not in profileList:
804 800 return False
805 801
806 802 return True
807 803
808 804 def run(self, dataOut, profileList=None, profileRangeList=None, beam=None, byblock=False, rangeList = None, nProfiles=None):
809 805
810 806 """
811 807 ProfileSelector:
812 808
813 809 Inputs:
814 810 profileList : Index of profiles selected. Example: profileList = (0,1,2,7,8)
815 811
816 812 profileRangeList : Minimum and maximum profile indexes. Example: profileRangeList = (4, 30)
817 813
818 814 rangeList : List of profile ranges. Example: rangeList = ((4, 30), (32, 64), (128, 256))
819 815
820 816 """
821 817
822 818 dataOut.flagNoData = True
823 819
824 820 if dataOut.flagDataAsBlock:
825 821 """
826 822 data dimension = [nChannels, nProfiles, nHeis]
827 823 """
828 824 if profileList != None:
829 825 dataOut.data = dataOut.data[:,profileList,:]
830 826 dataOut.nProfiles = len(profileList)
831 827 dataOut.profileIndex = dataOut.nProfiles - 1
832 828
833 829 if profileRangeList != None:
834 830 minIndex = profileRangeList[0]
835 831 maxIndex = profileRangeList[1]
836 832
837 833 dataOut.data = dataOut.data[:,minIndex:maxIndex+1,:]
838 834 dataOut.nProfiles = maxIndex - minIndex + 1
839 835 dataOut.profileIndex = dataOut.nProfiles - 1
840 836
841 837 if rangeList != None:
842 838 raise ValueError, "Profile Selector: Invalid argument rangeList. Not implemented for getByBlock yet"
843 839
844 840 dataOut.flagNoData = False
845 841
846 842 return True
847 843
848 844 """
849 845 data dimension = [nChannels, nHeis]
850 846 """
851 847
852 848 if nProfiles:
853 849 self.nProfiles = nProfiles
854 850 else:
855 851 self.nProfiles = dataOut.nProfiles
856 852
857 853 if profileList != None:
858 854
859 855 dataOut.nProfiles = len(profileList)
860 856
861 857 if self.isThisProfileInList(dataOut.profileIndex, profileList):
862 858 dataOut.flagNoData = False
863 859 dataOut.profileIndex = self.profileIndex
864 860
865 861 self.incIndex()
866 862 return True
867 863
868 864 if profileRangeList != None:
869 865
870 866 minIndex = profileRangeList[0]
871 867 maxIndex = profileRangeList[1]
872 868
873 869 dataOut.nProfiles = maxIndex - minIndex + 1
874 870
875 871 if self.isThisProfileInRange(dataOut.profileIndex, minIndex, maxIndex):
876 872 dataOut.flagNoData = False
877 873 dataOut.profileIndex = self.profileIndex
878 874
879 875 self.incIndex()
880 876 return True
881 877
882 878 if rangeList != None:
883 879
884 880 nProfiles = 0
885 881
886 882 for thisRange in rangeList:
887 883 minIndex = thisRange[0]
888 884 maxIndex = thisRange[1]
889 885
890 886 nProfiles += maxIndex - minIndex + 1
891 887
892 888 dataOut.nProfiles = nProfiles
893 889
894 890 for thisRange in rangeList:
895 891
896 892 minIndex = thisRange[0]
897 893 maxIndex = thisRange[1]
898 894
899 895 if self.isThisProfileInRange(dataOut.profileIndex, minIndex, maxIndex):
900 896
901 897 # print "profileIndex = ", dataOut.profileIndex
902 898
903 899 dataOut.flagNoData = False
904 900 dataOut.profileIndex = self.profileIndex
905 901
906 902 self.incIndex()
907 903 break
908 904 return True
909 905
910 906
911 907 if beam != None: #beam is only for AMISR data
912 908 if self.isThisProfileInList(dataOut.profileIndex, dataOut.beamRangeDict[beam]):
913 909 dataOut.flagNoData = False
914 910 dataOut.profileIndex = self.profileIndex
915 911
916 912 self.incIndex()
917 913
918 914 return True
919 915
920 916 raise ValueError, "ProfileSelector needs profileList, profileRangeList or rangeList parameter"
921 917
922 918 return False
923 919
924 920
925 921
926 922 class Reshaper(Operation):
927 923
928 924 def __init__(self):
929 925
930 926 Operation.__init__(self)
931 927 self.updateNewHeights = True
932 928
933 929 def run(self, dataOut, shape):
934 930
935 931 if not dataOut.flagDataAsBlock:
936 932 raise ValueError, "Reshaper can only be used when voltage have been read as Block, getBlock = True"
937 933
938 934 if len(shape) != 3:
939 935 raise ValueError, "shape len should be equal to 3, (nChannels, nProfiles, nHeis)"
940 936
941 937 shape_tuple = tuple(shape)
942 938 dataOut.data = numpy.reshape(dataOut.data, shape_tuple)
943 939 dataOut.flagNoData = False
944 940
945 941 if self.updateNewHeights:
946 942
947 943 old_nheights = dataOut.nHeights
948 944 new_nheights = dataOut.data.shape[2]
949 945 factor = 1.0*new_nheights / old_nheights
950 946
951 947 deltaHeight = dataOut.heightList[1] - dataOut.heightList[0]
952 948
953 949 xf = dataOut.heightList[0] + dataOut.nHeights * deltaHeight * factor
954 950
955 951 dataOut.heightList = numpy.arange(dataOut.heightList[0], xf, deltaHeight)
956 952
957 953 dataOut.nProfiles = dataOut.data.shape[1]
958 954
959 955 dataOut.ippSeconds *= factor
960 956 #
961 957 # import collections
962 958 # from scipy.stats import mode
963 959 #
964 960 # class Synchronize(Operation):
965 961 #
966 962 # isConfig = False
967 963 # __profIndex = 0
968 964 #
969 965 # def __init__(self):
970 966 #
971 967 # Operation.__init__(self)
972 968 # # self.isConfig = False
973 969 # self.__powBuffer = None
974 970 # self.__startIndex = 0
975 971 # self.__pulseFound = False
976 972 #
977 973 # def __findTxPulse(self, dataOut, channel=0, pulse_with = None):
978 974 #
979 975 # #Read data
980 976 #
981 977 # powerdB = dataOut.getPower(channel = channel)
982 978 # noisedB = dataOut.getNoise(channel = channel)[0]
983 979 #
984 980 # self.__powBuffer.extend(powerdB.flatten())
985 981 #
986 982 # dataArray = numpy.array(self.__powBuffer)
987 983 #
988 984 # filteredPower = numpy.correlate(dataArray, dataArray[0:self.__nSamples], "same")
989 985 #
990 986 # maxValue = numpy.nanmax(filteredPower)
991 987 #
992 988 # if maxValue < noisedB + 10:
993 989 # #No se encuentra ningun pulso de transmision
994 990 # return None
995 991 #
996 992 # maxValuesIndex = numpy.where(filteredPower > maxValue - 0.1*abs(maxValue))[0]
997 993 #
998 994 # if len(maxValuesIndex) < 2:
999 995 # #Solo se encontro un solo pulso de transmision de un baudio, esperando por el siguiente TX
1000 996 # return None
1001 997 #
1002 998 # phasedMaxValuesIndex = maxValuesIndex - self.__nSamples
1003 999 #
1004 1000 # #Seleccionar solo valores con un espaciamiento de nSamples
1005 1001 # pulseIndex = numpy.intersect1d(maxValuesIndex, phasedMaxValuesIndex)
1006 1002 #
1007 1003 # if len(pulseIndex) < 2:
1008 1004 # #Solo se encontro un pulso de transmision con ancho mayor a 1
1009 1005 # return None
1010 1006 #
1011 1007 # spacing = pulseIndex[1:] - pulseIndex[:-1]
1012 1008 #
1013 1009 # #remover senales que se distancien menos de 10 unidades o muestras
1014 1010 # #(No deberian existir IPP menor a 10 unidades)
1015 1011 #
1016 1012 # realIndex = numpy.where(spacing > 10 )[0]
1017 1013 #
1018 1014 # if len(realIndex) < 2:
1019 1015 # #Solo se encontro un pulso de transmision con ancho mayor a 1
1020 1016 # return None
1021 1017 #
1022 1018 # #Eliminar pulsos anchos (deja solo la diferencia entre IPPs)
1023 1019 # realPulseIndex = pulseIndex[realIndex]
1024 1020 #
1025 1021 # period = mode(realPulseIndex[1:] - realPulseIndex[:-1])[0][0]
1026 1022 #
1027 1023 # print "IPP = %d samples" %period
1028 1024 #
1029 1025 # self.__newNSamples = dataOut.nHeights #int(period)
1030 1026 # self.__startIndex = int(realPulseIndex[0])
1031 1027 #
1032 1028 # return 1
1033 1029 #
1034 1030 #
1035 1031 # def setup(self, nSamples, nChannels, buffer_size = 4):
1036 1032 #
1037 1033 # self.__powBuffer = collections.deque(numpy.zeros( buffer_size*nSamples,dtype=numpy.float),
1038 1034 # maxlen = buffer_size*nSamples)
1039 1035 #
1040 1036 # bufferList = []
1041 1037 #
1042 1038 # for i in range(nChannels):
1043 1039 # bufferByChannel = collections.deque(numpy.zeros( buffer_size*nSamples, dtype=numpy.complex) + numpy.NAN,
1044 1040 # maxlen = buffer_size*nSamples)
1045 1041 #
1046 1042 # bufferList.append(bufferByChannel)
1047 1043 #
1048 1044 # self.__nSamples = nSamples
1049 1045 # self.__nChannels = nChannels
1050 1046 # self.__bufferList = bufferList
1051 1047 #
1052 1048 # def run(self, dataOut, channel = 0):
1053 1049 #
1054 1050 # if not self.isConfig:
1055 1051 # nSamples = dataOut.nHeights
1056 1052 # nChannels = dataOut.nChannels
1057 1053 # self.setup(nSamples, nChannels)
1058 1054 # self.isConfig = True
1059 1055 #
1060 1056 # #Append new data to internal buffer
1061 1057 # for thisChannel in range(self.__nChannels):
1062 1058 # bufferByChannel = self.__bufferList[thisChannel]
1063 1059 # bufferByChannel.extend(dataOut.data[thisChannel])
1064 1060 #
1065 1061 # if self.__pulseFound:
1066 1062 # self.__startIndex -= self.__nSamples
1067 1063 #
1068 1064 # #Finding Tx Pulse
1069 1065 # if not self.__pulseFound:
1070 1066 # indexFound = self.__findTxPulse(dataOut, channel)
1071 1067 #
1072 1068 # if indexFound == None:
1073 1069 # dataOut.flagNoData = True
1074 1070 # return
1075 1071 #
1076 1072 # self.__arrayBuffer = numpy.zeros((self.__nChannels, self.__newNSamples), dtype = numpy.complex)
1077 1073 # self.__pulseFound = True
1078 1074 # self.__startIndex = indexFound
1079 1075 #
1080 1076 # #If pulse was found ...
1081 1077 # for thisChannel in range(self.__nChannels):
1082 1078 # bufferByChannel = self.__bufferList[thisChannel]
1083 1079 # #print self.__startIndex
1084 1080 # x = numpy.array(bufferByChannel)
1085 1081 # self.__arrayBuffer[thisChannel] = x[self.__startIndex:self.__startIndex+self.__newNSamples]
1086 1082 #
1087 1083 # deltaHeight = dataOut.heightList[1] - dataOut.heightList[0]
1088 1084 # dataOut.heightList = numpy.arange(self.__newNSamples)*deltaHeight
1089 1085 # # dataOut.ippSeconds = (self.__newNSamples / deltaHeight)/1e6
1090 1086 #
1091 1087 # dataOut.data = self.__arrayBuffer
1092 1088 #
1093 1089 # self.__startIndex += self.__newNSamples
1094 1090 #
1095 1091 # return No newline at end of file
General Comments 0
You need to be logged in to leave comments. Login now