DFreireF / tdms_scaler_reader

A fast reader for scaler channels for TDMS files

Geek Repo:Geek Repo

Github PK Tool:Github PK Tool

TDMS Scaler Reader

A fast reader for scaler channels for TDMS files.

Installation

pip install -r requirements.txt

Usage

python3 tdms_scaler_reader.py -c 5 -o . -n example ./PATH/TO/SCALER/DATA/*.tdms

Options:

  • -o: output file path, default is PWD
  • -n: output file name, default is "results"
  • -c: which channel, default is 5

Accessing data

The resulting file will be a compressed numpy file (npz) containing two arrays: frequency and time. You can access them like this:

import numpy as np
import matplotlib.pyplot as plt
d = np.load('example.npz')
plt.plot(d['t'], d['f'])

Explanation of the method

Creating difference between adjacent elements are done using np.diff. But, how about non adjacent elements? Imagine you have the array and the indexs of it:

Index Array Values
0 2
1 1
2 2
3 3
4 4
5 7
6 8
7 8
8 6
9 5
10 4
11 1

These are 12 values, i.e. indexes from 0 to 11. You are interested in getting a diff of every 4 elements, so from 12 values, you will have only 12/4 (three) values left by subtracting:

  • index 3 minus index 0 --> 3-2 = 1
  • index 7 minus index 4 --> 8-4 = 4
  • index 11 minus index 8 --> 1-6 = -5

so you shift the original array by -3, subtract from itself:

Index Shifted Array Values Array Values Difference
0 3 2 1
1 4 1 3
2 7 2 5
3 8 3 5
4 8 4 4
5 6 7 -1
6 5 8 -3
7 4 8 -4
8 1 6 -5
9 2 5 -3
10 1 4 -3
11 2 1 1

you see this is exactly what you want, only it contains more points than needed. You only need every 4th element using usual slicing [start:stop:step]system, like [::4], resulting in the first, middle and the last one which is what we want.

(a[3:]-a[:-3])[::4]
--> array([ 1,  4, -5])

Visually:

   |----------| (shifted array)
|----------|    (original array)
   |-------|    (difference)
   x   x   x    (values taken at indexes: 0,4,8)

In the case of our TDMS scaler files we do the same. Since we have 262144 kicker values and 256 time stamps, we have 1024 count points. In other words, we have a sampling time of the kicker signal of almost 1 ms, which means that the standard deviation of the mapping between time stamp and kicker signal is of 1 seconds by using this method. So in case of 256 time stamps. delta_t is calculated using np.diff directly, since TimeDelta64 elements are adjacent. In between those time stamps, the counter counts up, every time there is a pulse on the scaler. So to determine the number of counts in each section, the count difference between the value directly on top of the time stamp, and the last value just before the next time stamp. e.g.: value at index 1023 - value at index 0, value at index 2047 - value at index 1024 and so on. This is achieved by the method above for delta_cnt and results again in 256 values. Then delta_cnt / delta_t gives us a value in frequency [Hz]. The time stamp values are aligned to the left of 1024 data points, so the last bin must be left out.

About

A fast reader for scaler channels for TDMS files

License:GNU General Public License v3.0


Languages

Language:Python 100.0%