我想读取一个.txt文件并从中获取数据,然后想出一种方法来找出它的某个块中有多少个峰值。我有一个Geiger计数器,它将运行一段时间,其输出将被记录在一个文件中,我称之为'NuclearCounting.txt'。你可以看到前100行here。你可以看到平均值约为1.7,很少达到~3或下降到~1。
我想将数据分成一分钟或一分钟(在这种情况下我选择秒),并分析每个时间间隔内发生的'事件'数量。我通过将'事件'称为数据的最大值或最小值来做到这一点。由于背景辐射会产生一些噪音,因此我希望在那里有一条线说“峰值”必须与平均值相差3 s.d.如果可能的话。
以下是目前的代码:
import numpy as np
import matplotlib.pyplot as plt
from scipy import signal
import scipy.stats
x1 = []
y1 = []
f = open("NC.txt", "r")
for line in f:
line = line.strip()
parts = line.split(",") #Separated by commas and spaces
time = float(parts[1]) #This column is the column recording time
value = float(parts[2]) #This one records the value the detector reads.
x1.append(time)
y1.append(value)
f.close()
xv = np.array(x1) #Time
yv = np.array(y1) #Values recorded
#Statistics
m = np.mean(yv)
d = np.std(yv)
timetot = int(round(np.max(xv))) #This gives the total time in seconds to the nearest second. I use this to break it into chunks of one second of data each.
#Counting events
def chunk(l, n):
n = max(1, n)
return [l[k:k+n] for k in range(0, len(l), n)]
t = chunk(xv,timetot) #Breaking the time into chunks of a second
v = chunk(yv,timetot) #Doing the same for the values recorded by the detector
i = []
for x in v:
peak = signal.find_peaks_cwt(x, np.arange(2,10)) #This is the problem area
i.append(peak)
print(len(i))
数组i用于存储我得到的“峰值”数。我只想知道每个区间的长度。问题是输出是python告诉我我有25000个峰值。这是没有意义的。每秒,我应该只获得最多的几个计数。它也只是给了我一个完全由15条目输入的数组。
有人可以告诉我如何纠正这个问题吗?我不知道为什么scipy函数不起作用,当然也不知道为什么它应该在没有数据条目具有该值时吐出15。
感谢。
答案 0 :(得分:1)
代码中的列表i
并不存储每个块的峰值数,而是存储峰值索引。
为了计算峰值,您需要使用i.append(len(peak))
。如果您还希望将峰值约束为大于中位数的3个标准差,则可以peak = np.sum(x[signal.find_peaks_cwt(x, np.arange(2,10))] > 3*d)
。
最后但并非最不重要的是print(len(i))
将返回峰值列表的长度,即块的数量。我想你想要的是找出每个块的峰数。所以,总而言之,我认为这就是你想要的。
for x in v:
peak_index = signal.find_peaks_cwt(x, np.arange(2,10))
peak_sum = np.sum(x[peak_index] > 3*d)
i.append(peak_sum)
for p in i:
print(p)