jiahaohappy 2020-05-28
就是一个批量读取文件, 然后计算指标的过程. 难度到是没啥, 只是想记录一把, 毕竟这类的需求, 其实还是蛮多的.
但涉及一些数据的安全, 和指标这块也是不能透露的, 因此只能是贴上代码, 目的还是给自己以后做参考的. 代码中有个常数, 其实表示每个文件, 每行的同位置的值, 是一样的. 是发现规律了, 最开始是找近似, 去最为接近的一条, 后来写完发现, 根本不用不动. 然后, 文本数据, 就是后缀不是常用的, Excel, Csv.. 这种, 给我有个 xx.sed 从未见过的这类. 还好我基本功可以, 毕竟当年抄过书本, read_table 这类的骚操作, 就恰好满足需求了.
因为涉及的数据不能公开, 业务这块也不能谈及, 指标计算比较多和杂. 总之是给我自己看的, 并未作为分享的.
from os import listdir import pandas as pd from math import log10 import time # 发现数据规律, 每个文件的第一列值 Wvl 都是固定的, 直接取即可 # 每个指标值行索引(Wvl)可以先全部找出来 R990 = 990.4 R720 = 719.5 R860 = 860.2 R790 = 789.7 R670 = 669.4 R730 = 730.2 R525 = 525.2 R750 = 749.9 R705 = 704.8 R445 = 444.5 R550 = 550.1 R870 = 869.5 R680 = 680.3 R810 = 809.7 R800 = 799.7 R700 = 699.4 R840 = 840.1 R1510 = 1511.8 R1680 = 1681.2 start = time.time() ret = [] # 结果 my_dir = ‘./光谱数据集/‘ file_list = listdir(my_dir) for cur_file in file_list: print("正在处理:", cur_file) df = None try: df = pd.read_table(my_dir + cur_file, skiprows=26) # df[‘nb‘] = df[‘Raw Counts (Ref.)‘] - df[‘Raw Counts (Target)‘] df[‘nb‘] = round(df[‘Reflect. %‘] / 100, 2) df = df.set_index(‘Wvl‘)[‘nb‘] except Exception as e: print("出错啦, 大兄弟!", e) # 计算着一大坨数据指标 cur_lst = [] # 被文件名作为 第一个数据 cur_lst.append(cur_file) # RSI rsi = df.loc[R990] / df.loc[R720] cur_lst.append(rsi) # NDSI ndsi = (df.loc[R860] - df.loc[R720]) / (df.loc[R860] + df.loc[R720]) cur_lst.append(ndsi) # FD_NDVI fdndvi = (df.loc[R730] - df.loc[R525]) / (df.loc[R730] + df.loc[R525]) cur_lst.append(fdndvi) # RENDVI cur_lst.append((df.loc[R750] - df.loc[R705]) / (df.loc[R750] + df.loc[R705])) # mNd705 cur_lst.append((df.loc[R750] - df.loc[R705]) / (df.loc[R750] + 2 * df.loc[R445])) # GNDVI cur_lst.append((df.loc[R790] - df.loc[R550]) / (df.loc[R790] + df.loc[R550])) # SAVI cur_lst.append(1.5 * (df.loc[R870] - df.loc[R680]) / (df.loc[R870] + df.loc[R680] + 0.16)) # OSIVI cur_lst.append(1.16 * (df.loc[R810] - df.loc[R680]) / (df.loc[R810] - df.loc[R680] + 0.16)) # MSAVI cur_lst.append( 2 * (df.loc[R800] + 1 - ((2 * df.loc[R800] + 1) * 2 - 8 * (df.loc[R800] - df.loc[R670])) * 0.5) ) # DCNA cur_lst.append( (df.loc[R720] - df.loc[R700]) / (df.loc[R700] - df.loc[R670]) / (df.loc[R700] - df.loc[R670] + 0.03) ) # CIgreen cur_lst.append(((df.loc[R840] - df.loc[R870]) / df.loc[R550]) - 1) # NINI try: cur_lst.append( (log10(1 / df.loc[R1510]) - log10(1 / df.loc[R1680])) / (log10(1 / df.loc[R1510]) + log10(1 / df.loc[R1680])) ) except: print(cur_file, "log 计算有问题") cur_lst.append(‘lg计算失败‘) # TVI cur_lst.append( 0.5 * (120 * (df.loc[R750] - df.loc[R550]) - 200 * (df.loc[R670] - df.loc[R550])) ) # DSI cur_lst.append(df.loc[R800] - df.loc[R680]) # 将当前结果添加到 ret 中 ret.append(cur_lst) # 最后将 [[],[]...] 再存为 DataFrame col = [‘数据文件名‘, ‘RSI‘, ‘NDSI‘, ‘FD_NDVI‘, ‘RENDVI‘, ‘mNd705‘, ‘GNDVI‘, ‘SAVI‘, ‘OSIVI‘, ‘MSAVI‘, ‘DCNA‘, ‘CIgreen‘, ‘NINI‘, ‘TVI‘,‘DSI‘] data = pd.DataFrame(ret, columns=col) print() print("*"*50) print("正在存储到, 表格...") data.to_excel("D:/光谱数据.xlsx", index=False) end = time.time() print(f"处理完毕! 共处理 {len(file_list)} 个文件, 总共用时 {round(end - start, 2)} 秒") print("*"*50)
其实蛮简单的一个脚本, 循环读取文件夹的数据, 然后来弄即可. 发现现在这换了 台式电脑, 果然很稳, 同时 读取 文本数据, 远比 Excel 文件, 效率高了 近 10倍.
正在处理: 20190930_00128.sed 正在处理: 20190930_00129.sed 正在处理: 20190930_00130.sed 正在处理: 20190930_00131.sed 正在处理: 20190930_00132.sed 正在处理: 20190930_00133.sed 正在处理: 20190930_00134.sed 正在处理: 20190930_00135.sed 正在处理: 20190930_00136.sed 正在处理: 20190930_00137.sed 正在处理: 20190930_00138.sed 正在处理: 20190930_00139.sed 正在处理: 20190930_00140.sed 正在处理: 20190930_00141.sed 正在处理: 20190930_00142.sed 正在处理: 20190930_00143.sed 正在处理: 20190930_00144.sed 正在处理: 20190930_00145.sed 正在处理: 20190930_00146.sed 正在处理: 20190930_00147.sed ...... ************************************************** 正在存储到, 表格... 处理完毕! 共处理 1447 个文件, 总共用时 5.58 秒 ************************************************** [Finished in 6.1s]
计算的时候总共分3步,1到2是第二组......lower: i. 这组数据中的小值 higher: j. 这组数据中的大值,fraction 是第三步中的小数部分,意思是当前这组数据的0到1的分位数
Series是一种类似于一维数组的对象,由一组数据以及一组与之对应的索引组成。 index: 索引序列,必须是唯一的,且与数据的长度相同. 如果没有传入索引参数,则默认会自动创建一个从0~N的整数索引