@@ -467,7 +467,7 @@ def rdsegment(filename, dirname, pbdir, nsig, fmt, siglen, byteoffset,
467
467
if smoothframes or sum (sampsperframe )== nsig :
468
468
469
469
# Allocate signal array
470
- signals = np .empty ([sampto - sampfrom , len (channels )], dtype = 'int64' )
470
+ signals = np .zeros ([sampto - sampfrom , len (channels )], dtype = 'int64' )
471
471
472
472
# Read each wanted dat file and store signals
473
473
for fn in w_filename :
@@ -539,7 +539,6 @@ def rddat(filename, dirname, pbdir, fmt, nsig,
539
539
540
540
# Total number of bytes to be processed in intermediate step.
541
541
totalprocessbytes = requiredbytenum ('read' , fmt , totalprocesssamples )
542
-
543
542
544
543
# Get the intermediate bytes or samples to process. Bit of a discrepancy. Recall special formats
545
544
# load uint8 bytes, other formats already load samples.
@@ -560,9 +559,9 @@ def rddat(filename, dirname, pbdir, fmt, nsig,
560
559
561
560
# Read the required bytes from the dat file.
562
561
# Then continue to process the read values into proper samples
563
- if fmt == '212' :
564
-
565
- # Clear memory???
562
+
563
+ # Special formats
564
+ if fmt in [ '212' , '310' , '311' ]:
566
565
567
566
# No extra samples/frame. Obtain original uniform numpy array
568
567
if tsampsperframe == nsig :
@@ -584,22 +583,22 @@ def rddat(filename, dirname, pbdir, fmt, nsig,
584
583
elif smoothframes :
585
584
586
585
# Turn the bytes into actual samples. Flat 1d array. All samples for all frames.
587
- sigflat = bytes2samples (sigbytes , totalprocesssamples , fmt )
586
+ sigbytes = bytes2samples (sigbytes , totalprocesssamples , fmt )
588
587
589
588
# Remove extra leading sample read within the byte block if any
590
589
if blockfloorsamples :
591
- sigflat = sigflat [blockfloorsamples :]
590
+ sigbytes = sigbytes [blockfloorsamples :]
592
591
593
- # Smoothed signal
594
- sig = np .zeros ((int (len (sigflat )/ tsampsperframe ) , nsig ))
592
+ # Allocate memory for smoothed signal
593
+ sig = np .zeros ((int (len (sigbytes )/ tsampsperframe ) , nsig ), dtype = 'int64' )
595
594
596
595
# Transfer and average samples
597
596
for ch in range (nsig ):
598
597
if sampsperframe [ch ] == 1 :
599
- sig [:, ch ] = sigflat [sum (([0 ] + sampsperframe )[:ch + 1 ])::tsampsperframe ]
598
+ sig [:, ch ] = sigbytes [sum (([0 ] + sampsperframe )[:ch + 1 ])::tsampsperframe ]
600
599
else :
601
600
for frame in range (sampsperframe [ch ]):
602
- sig [:, ch ] += sigflat [sum (([0 ] + sampsperframe )[:ch + 1 ]) + frame ::tsampsperframe ]
601
+ sig [:, ch ] += sigbytes [sum (([0 ] + sampsperframe )[:ch + 1 ]) + frame ::tsampsperframe ]
603
602
sig = (sig / sampsperframe )
604
603
605
604
# Skew the signal
@@ -608,28 +607,23 @@ def rddat(filename, dirname, pbdir, fmt, nsig,
608
607
# Extra frames present without wanting smoothing. Return all expanded samples.
609
608
else :
610
609
# Turn the bytes into actual samples. Flat 1d array. All samples for all frames.
611
- sigflat = bytes2samples (sigbytes , totalprocesssamples , fmt )
610
+ sigbytes = bytes2samples (sigbytes , totalprocesssamples , fmt )
612
611
613
612
# Remove extra leading sample read within the byte block if any
614
613
if blockfloorsamples :
615
- sigflat = sigflat [blockfloorsamples :]
614
+ sigbytes = sigbytes [blockfloorsamples :]
616
615
617
616
# Arranged signals
618
617
sig = []
619
618
620
619
# Transfer over samples
621
620
for ch in range (nsig ):
622
621
# Indices of the flat signal that belong to the channel
623
- ch_indices = np .concatenate (([np .array (range (sampsperframe [ch ])) + sum ([0 ]+ sampsperframe [:ch ]) + tsampsperframe * framenum for framenum in range (int (len (sigflat )/ tsampsperframe ))]))
624
- sig .append (sigflat [ch_indices ])
622
+ ch_indices = np .concatenate (([np .array (range (sampsperframe [ch ])) + sum ([0 ]+ sampsperframe [:ch ]) + tsampsperframe * framenum for framenum in range (int (len (sigbytes )/ tsampsperframe ))]))
623
+ sig .append (sigbytes [ch_indices ])
625
624
626
625
# Skew the signal
627
626
sig = skewsig (sig , skew , nsig , readlen , fmt , nanreplace , sampsperframe )
628
-
629
- elif fmt == '310' :
630
- pass
631
- elif fmt == '311' :
632
- pass
633
627
# Simple format signals that are loaded as they are stored.
634
628
else :
635
629
# Adjust for skew, reshape, and consider sampsperframe.
@@ -640,9 +634,6 @@ def rddat(filename, dirname, pbdir, fmt, nsig,
640
634
elif fmt == '160' :
641
635
sigbytes = sigbytes - 32768
642
636
643
- #print('sigbytes:', sigbytes)
644
-
645
-
646
637
# No extra samples/frame. Obtain original uniform numpy array
647
638
if tsampsperframe == nsig :
648
639
@@ -656,19 +647,20 @@ def rddat(filename, dirname, pbdir, fmt, nsig,
656
647
# Extra frames present to be smoothed. Obtain averaged uniform numpy array
657
648
elif smoothframes :
658
649
659
- # Allocate memory for signal
660
- sig = np .empty ([ readlen , nsig ] , dtype = 'int ' )
650
+ # Allocate memory for smoothed signal
651
+ sig = np .zeros (( int ( len ( sigbytes ) / tsampsperframe ) , nsig ) , dtype = 'int64 ' )
661
652
662
- # Samples are averaged within frames
663
- # Obtain the correct samples, factoring in skew
653
+ # Transfer and average samples
664
654
for ch in range (nsig ):
665
655
if sampsperframe [ch ] == 1 :
666
- sig [:, ch ] = sigbytes [skew [ ch ] * tsampsperframe + sum (([0 ] + sampsperframe )[:ch + 1 ])::tsampsperframe ]
656
+ sig [:, ch ] = sigbytes [sum (([0 ] + sampsperframe )[:ch + 1 ])::tsampsperframe ]
667
657
else :
668
658
for frame in range (sampsperframe [ch ]):
669
- sig [:, ch ] += sigbytes [skew [ ch ] * tsampsperframe + sum (([0 ] + sampsperframe )[:ch + 1 ]) + frame ::tsampsperframe ]
659
+ sig [:, ch ] += sigbytes [sum (([0 ] + sampsperframe )[:ch + 1 ]) + frame ::tsampsperframe ]
670
660
sig = (sig / sampsperframe )
671
661
662
+ # Skew the signal
663
+ sig = skewsig (sig , skew , nsig , readlen , fmt , nanreplace )
672
664
673
665
# Extra frames present without wanting smoothing. Return all expanded samples.
674
666
else :
@@ -677,14 +669,8 @@ def rddat(filename, dirname, pbdir, fmt, nsig,
677
669
678
670
# Transfer over samples
679
671
for ch in range (nsig ):
680
- # chansig = np.zeros(readlen*sampsperframe[ch], dtype='int')
681
- # for frame in range(sampsperframe[ch]):
682
- # chansig[frame::sampsperframe[ch]] = sigbytes[skew[ch]*tsampsperframe+sum(([0] + sampsperframe)[:ch + 1]) + frame::tsampsperframe]
683
- # sig.append(chansig)
684
-
685
- # Get the sample indices of the channel samples to transfer over
672
+ # Indices of the flat signal that belong to the channel
686
673
ch_indices = np .concatenate ([np .array (range (sampsperframe [ch ])) + sum ([0 ]+ sampsperframe [:ch ]) + tsampsperframe * framenum for framenum in range (int (len (sigbytes )/ tsampsperframe ))])
687
-
688
674
sig .append (sigbytes [ch_indices ])
689
675
690
676
# Skew the signal
@@ -848,11 +834,12 @@ def getdatbytes(filename, dirname, pbdir, fmt, startbyte, nsamp):
848
834
return sigbytes
849
835
850
836
851
- # Converts loaded uint8 blocks into samples for special formats
852
- def bytes2samples (sigbytes , nsamp , fmt ):
853
837
838
+ def bytes2samples (sigbytes , nsamp , fmt ):
839
+ """
840
+ Converts loaded uint8 blocks into samples for special formats
841
+ """
854
842
if fmt == '212' :
855
-
856
843
# Easier to process when dealing with whole blocks
857
844
if nsamp % 2 :
858
845
nsamp = nsamp + 1
@@ -877,19 +864,69 @@ def bytes2samples(sigbytes, nsamp, fmt):
877
864
# Loaded values as unsigned. Convert to 2's complement form:
878
865
# values > 2^11-1 are negative.
879
866
sig [sig > 2047 ] -= 4096
880
- sig [sig > 2047 ] -= 4096
881
867
882
868
elif fmt == '310' :
883
- pass
869
+ # Easier to process when dealing with whole blocks
870
+ if nsamp % 3 :
871
+ nsamp = upround (nsamp ,3 )
872
+ addedsamps = nsamp % 3
873
+ sigbytes = np .append (sigbytes , np .zeros (addedsamps , dtype = 'uint8' ))
874
+ else :
875
+ addedsamps = 0
876
+
877
+ # 1d array of actual samples. Fill the individual triplets.
878
+ sig = np .zeros (nsamp , dtype = 'int64' )
879
+
880
+ # One sample triplet is stored in one byte quartet
881
+ # First sample is 7 msb of first byte and 3 lsb of second byte.
882
+ sig [0 ::3 ] = (sigbytes [0 ::4 ] >> 1 )[0 :len (sig [0 ::3 ])] + 128 * np .bitwise_and (sigbytes [1 ::4 ], 0x07 )[0 :len (sig [0 ::3 ])]
883
+ # Second signal is 7 msb of third byte and 3 lsb of forth byte
884
+ sig [1 ::3 ] = (sigbytes [2 ::4 ] >> 1 )[0 :len (sig [1 ::3 ])] + 128 * np .bitwise_and (sigbytes [3 ::4 ], 0x07 )[0 :len (sig [1 ::3 ])]
885
+ # Third signal is 5 msb of second byte and 5 msb of forth byte
886
+ sig [2 ::3 ] = np .bitwise_and ((sigbytes [1 ::4 ] >> 3 ), 0x1f )[0 :len (sig [2 ::3 ])] + 32 * np .bitwise_and (sigbytes [3 ::4 ] >> 3 , 0x1f )[0 :len (sig [2 ::3 ])]
887
+
888
+ # Remove trailing samples read within the byte block if originally not 3n sampled
889
+ if addedsamps :
890
+ sig = sig [:- addedsamps ]
891
+
892
+ # Loaded values as unsigned. Convert to 2's complement form:
893
+ # values > 2^9-1 are negative.
894
+ sig [sig > 511 ] -= 1024
884
895
885
896
elif fmt == '311' :
886
- pass
897
+ # Easier to process when dealing with whole blocks
898
+ if nsamp % 3 :
899
+ nsamp = upround (nsamp ,3 )
900
+ addedsamps = nsamp % 3
901
+ sigbytes = np .append (sigbytes , np .zeros (addedsamps , dtype = 'uint8' ))
902
+ else :
903
+ addedsamps = 0
904
+
905
+ # 1d array of actual samples. Fill the individual triplets.
906
+ sig = np .zeros (nsamp , dtype = 'int64' )
907
+
908
+ # One sample triplet is stored in one byte quartet
909
+ # First sample is first byte and 2 lsb of second byte.
910
+ sig [0 ::3 ] = sigbytes [0 ::4 ][0 :len (sig [0 ::3 ])] + 256 * np .bitwise_and (sigbytes [1 ::4 ], 0x03 )[0 :len (sig [0 ::3 ])]
911
+ # Second sample is 6 msb of second byte and 4 lsb of third byte
912
+ sig [1 ::3 ] = (sigbytes [1 ::4 ] >> 2 )[0 :len (sig [1 ::3 ])] + 64 * np .bitwise_and (sigbytes [2 ::4 ], 0x0f )[0 :len (sig [1 ::3 ])]
913
+ # Third sample is 4 msb of third byte and 6 msb of forth byte
914
+ sig [2 ::3 ] = (sigbytes [2 ::4 ] >> 4 )[0 :len (sig [2 ::3 ])] + 16 * np .bitwise_and (sigbytes [3 ::4 ], 0x7f )[0 :len (sig [2 ::3 ])]
915
+
916
+ # Remove trailing samples read within the byte block if originally not 3n sampled
917
+ if addedsamps :
918
+ sig = sig [:- addedsamps ]
919
+
920
+ # Loaded values as unsigned. Convert to 2's complement form:
921
+ # values > 2^9-1 are negative.
922
+ sig [sig > 511 ] -= 1024
887
923
return sig
888
924
889
925
890
- # Skew the signal and shave off extra samples
891
926
def skewsig (sig , skew , nsig , readlen , fmt , nanreplace , sampsperframe = None ):
892
927
"""
928
+ Skew the signal, insert nans and shave off end of array if needed.
929
+
893
930
fmt is just for the correct nan value.
894
931
sampsperframe is only used for skewing expanded signals.
895
932
"""
@@ -1202,7 +1239,7 @@ def processwfdbbytes(filename, dirname, pbdir, fmt, startbyte, readlen, nsig, sa
1202
1239
# At least one channel has multiple samples per frame. Extra samples are averaged.
1203
1240
else :
1204
1241
# Keep the first sample in each frame for each channel
1205
- sig = np .empty ([readlen , nsig ])
1242
+ sig = np .zeros ([readlen , nsig ])
1206
1243
for ch in range (0 , nsig ):
1207
1244
if sampsperframe [ch ] == 1 :
1208
1245
sig [:, ch ] = sigbytes [sum (([0 ] + sampsperframe )[:ch + 1 ])::tsampsperframe ]
@@ -1222,68 +1259,6 @@ def processwfdbbytes(filename, dirname, pbdir, fmt, startbyte, readlen, nsig, sa
1222
1259
1223
1260
1224
1261
1225
-
1226
-
1227
-
1228
-
1229
-
1230
-
1231
-
1232
-
1233
-
1234
-
1235
-
1236
- # OLD! DO NOT USE
1237
- def skewsignal (sig , skew , filename , dirname , pbdir , nsig , fmt , siglen , sampfrom , sampto , startbyte ,
1238
- bytesloaded , byteoffset , sampsperframe ):
1239
-
1240
- # Total number of samples per frame.
1241
- tsampsperframe = sum (sampsperframe )
1242
-
1243
- if max (skew ) > 0 :
1244
- # Array of samples to fill in the final samples of the skewed channels.
1245
- extrasig = np .empty ([max (skew ), nsig ])
1246
- extrasig .fill (digi_nan (fmt ))
1247
-
1248
- # Load the extra samples if the end of the file hasn't been reached.
1249
- if siglen - (sampto - sampfrom ):
1250
- startbyte = startbyte + bytesloaded
1251
- # Point the the file pointer to the start of a block of 3 or 4 and
1252
- # keep track of how many samples to discard after reading. For
1253
- # regular formats the file pointer is already at the correct
1254
- # location.
1255
- if fmt == '212' :
1256
- # Extra samples to read
1257
- floorsamp = (startbyte - byteoffset ) % 3
1258
- # Now the byte pointed to is the first of a byte triplet
1259
- # storing 2 samples. It happens that the extra samples match
1260
- # the extra bytes for fmt 212
1261
- startbyte = startbyte - floorsamp
1262
- elif (fmt == '310' ) | (fmt == '311' ):
1263
- floorsamp = (startbyte - byteoffset ) % 4
1264
- # Now the byte pointed to is the first of a byte quartet
1265
- # storing 3 samples.
1266
- startbyte = startbyte - floorsamp
1267
-
1268
- # The length of extra signals to be loaded
1269
- extraloadlen = min (siglen - (sampto - sampfrom ), max (skew ))
1270
-
1271
- # Array of extra loaded samples
1272
- extraloadedsig = processwfdbbytes (filename , dirname , pbdir ,
1273
- fmt , startbyte , extraloadlen , nsig , sampsperframe , floorsamp )[0 ]
1274
-
1275
- # Fill in the extra loaded samples
1276
- extrasig [:extraloadedsig .shape [0 ], :] = extraloadedsig
1277
-
1278
- # Fill in the skewed channels with the appropriate values.
1279
- for ch in range (0 , nsig ):
1280
- if skew [ch ] > 0 :
1281
- sig [:- skew [ch ], ch ] = sig [skew [ch ]:, ch ]
1282
- sig [- skew [ch ]:, ch ] = extrasig [:skew [ch ], ch ]
1283
- return sig
1284
-
1285
-
1286
-
1287
1262
# Bytes required to hold each sample (including wasted space) for
1288
1263
# different wfdb formats
1289
1264
bytespersample = {'8' : 1 , '16' : 2 , '24' : 3 , '32' : 4 , '61' : 2 ,
@@ -1458,10 +1433,6 @@ def wrdatfile(filename, fmt, d_signals, byteoffset, expanded=False, e_d_signals=
1458
1433
for framenum in range (spf ):
1459
1434
d_signals [:, expand_ch ] = e_d_signals [ch ][framenum ::spf ]
1460
1435
expand_ch = expand_ch + 1
1461
-
1462
- # ch_indices = np.concatenate(([np.array(range(sampsperframe[ch])) + sum([0]+sampsperframe[:ch]) + tsampsperframe*framenum for framenum in range(int(len(sigflat)/tsampsperframe))]))
1463
- # sig.append(sigflat[ch_indices])
1464
- # d_signals[] = e_d_signals[ch]
1465
1436
1466
1437
# This nsig is used for making list items.
1467
1438
# Does not necessarily represent number of signals (ie. for expanded=True)
0 commit comments