浅析Numpy.genfromtxt及File I/O讲解

Python 并没有提供数组功能,虽然列表 (list) 可以完成基本的数组功能,但它并不是真正的数组,而且在数据量较大时,使用列表的速度就会慢的让人难受。为此,Numpy 提供了真正的数组功能,以及对数据快速处理的函数。Numpy 还是很多更高级的扩展库的依赖库,例如: ScipyMatplotlibPandas等。此外,值得一提的是:Numpy 内置函数处理数据的速度是 C 语言级别的,因此编写程序时,应尽量使用内置函数,避免出现效率瓶颈的现象。一切计算源于数据,那么我们就来看一看Numpy.genfromtxt 如何优雅的处理数据。

官方文档

Enthought offical tutorial: numpy.genfromtxt

A very common file format for data file is comma-separated values (CSV), or related formats such as TSV (tab-separated values). To read data from such files into Numpy arrays we can use the numpy.genfromtxt function.

案例说明

我们以数字示波器采集的实验产生的三角波 (triangular waveform) 为例,它是包含数据信息的表头,以 .txt 格式存储的文本文件。

Type: raw 
Points: 16200 
Count: 1 
... 
X Units: second 
Y Units: Volt 
XY Data: 
2.4000000E-008, 1.4349E-002 
2.4000123E-008, 1.6005E-002 
2.4000247E-008, 1.5455E-002 
2.4000370E-008, 1.5702E-002 
2.4000494E-008, 1.5147E-002 
... 

Python 获取数据的方式有很多:(1) 如果在命令行运行 Python 脚本,你可以用 sys.stdinsys.stdout 以管道 (pipe) 方式传递数据;(2) 可以显式地用代码来读写文件获取数据;(3) 从网页获取数据,也就是所谓的爬虫 (web spider);(4) 使用 API (Application Programming Interface) 获取结构化格式的数据。 而在科学计算领域,更多的是处理实验中所获得的数据,比如:传感器,采集卡,示波器,光谱仪等仪器采集的数据。

案例一:温度传感器 (temperature sensor) 数据

本案例所采用的数据是热敏电阻 (thermistor) 采集的被加热物体的温度信息数据,其以如下格式存储在txt文件中:

2018-02-15 21:31:08.781 49.9492 
2018-02-15 21:31:09.296 49.9589 
2018-02-15 21:31:09.811 49.964 
2018-02-15 21:31:10.326 49.9741 
2018-02-15 21:31:10.841 49.983
...

处理文本文件的第一步是通过 open 命令来获取一个文件对象

file_for_reading = open('thermistor.txt', 'r') # 'r' 意味着只读 
file_for_writing = open('thermistor.txt', 'w') # 'w' 是写入 
file_for_appending = open('thermistor.txt', 'a') # 'a' 是添加 
file_for_xxx.close() # 完成操作后要关闭文件 

因为非常容易忘记关闭文件,所以应该在 with 程序块里操作文件,这样结尾处文件会被自动关闭:

with open('thermistor.txt', 'r') as f:data = function_that_gets_data_form(f) # 获取数据函数

此时,f 已经关闭了,就不能试图使用它啦,然后对数据执行相应的操作即可。

process(data) # 处理数据函数
处理文本文件第二步是观察数据特征,选择合适的读取命令:通过观察,可以发现,文件没有头部,每一行包括三种数据 (编号,时间,温度) 他们之间以空格键分开,每一列是同一类数据,这样我们就可以用 Python 中的 csv 模块中的 csv.reader 对其进行迭代处理,每一行都会被处理成恰当划分的列表。
 1 import csv 
 2 with open(r"thermistor.txt","rb") as f: 
 3       reader = csv.reader(f,delimiter='\t') 
 4       number=[] 
 5       time = [] 
 6       data=[] 
 7       for row in reader: 
 8            number.append(row[0]) 
 9            time.append(row[1])  
10            data.append(float(row[2])) 

处理文本文件的第三步是检测数据读取格式是否正确,我们可以用如下的方式检测:

>>> print number[0], time[0], data[0] 
>>> 2018-02-15 21:31:08.781 49.9492

从输出的首个元素来看,以上的读取数据的方式是没有问题的,但是到这里我们并不能完全放心我们的数据格式:

>>> print number[0:3], time[0:3], data[0:3] 
>>> ['\xef\xbb\xbf1', '2', '3']
['2018-02-15 21:31:08.781', '2018-02-15 21:31:09.296', '2018-02-15 21:31:09.811'] 
[49.9492, 49.9589, 49.964] 
当我们以列表的形式输出时,number 中的首个元素出现了我们没有预料到的“乱码”,这其实是 BOM (byte order mark), 它是为 UTF-16 和 UTF-32 准备的,用以标记字节序。微软在 UTF-8 中使用 BOM 是因为这样可以把 UTF-8 和 ASCII 等编码区别开,但这样的文件会给我们的数据读取带来问题。还好,我们可以用 Python 中的 codecs 模块解决这个问题。
1 import csv 
2 import codecs 
3 with codecs.open(r"thermistor.txt","rb","utf-8-sig") as f: 
4     reader = csv.reader(f,delimiter='\t') 
5     number=[] time=[] data=[] 
6     for row in reader: 
7         number.append(row[0]) 
8         time.append(row[1]) 
9         data.append(float(row[2])

此时,我们再以列表形式输出时,就会得到正确的结果:

>>> ['1', '2', '3'] 
['2018-02-15 21:31:08.781', '2018-02-15 21:31:09.296', '2018-02-15 21:31:09.811'] 
[49.9492, 49.9589, 49.964]

然后就可以用得到的数据进行处理分析啦~

案例二:示波器 (oscilloscope) 数据

有了上面的经验,我们直接从处理文本文件第二步开始,示波器数据相对上面的数据,复杂的地方在于它包含了表头信息,而这些信息大部分时间是处理数据中不太需要的,它的数据格式如下:

Type: raw 
Points: 16200 
Count: 1 
XInc: 1.23457E-013 
XOrg: 2.4000000000E-008 
YData range: 1.48000E-001 
YData center: 5.00000E-004 
Coupling: 50 
Ohms XRange: 2.00000E-009 
XOffset: 2.4000000000E-008 
YRange: 1.44000E-001 
YOffset: 5.00000E-004 
Date: 15 APR 2018 
Time: 16:00:54:74 
Frame: 86100C:MY46520443 
X Units: second 
Y Units: Volt 
XY Data: 
2.4000000E-008, 1.4349E-002 
2.4000123E-008, 1.6005E-002 
2.4000247E-008, 1.5455E-002 
2.4000370E-008, 1.5702E-002 
2.4000494E-008, 1.5147E-002 
... 

可以看出,“表头”是一些参数信息,真正有用的数据是从 “XY Data:” 下一行开始的,对于这样的数据有两种方法进行读取:(1) 直接跳过“表头”读取数据;(2) 利用正则表达式寻找“表头” 和数据的不同特征进行识别读取。

1 with open(r"waveform.txt","rb") as f: 
2     lines = f.readlines() x=[] y=[] 
3     for line in lines[18:]: 
4         x.append(float(line.replace("\r\n","").split(",")[0])) 
5         y.append(float(line.replace("\r\n","").split(",")[1]))

通过观察我们发现有效数据是从第19行开始的,于是我们直接从19行开始读取数据,跳过“表头”,以列表形式输出 x 和 y 前3个元素如下:

>>> [2.4e-08, 2.4000123e-08, 2.4000247e-08] 
[0.014349, 0.016005, 0.015455] # 数据读取正确

运用正则表达式读取数据的关键在于找到有效数据行的独有特征,这里以 “E-002” 作为有效数据行区别于“表头”的特征,对数据的读取方式如下:

1 import re 
2 with open(r"waveform.txt","rb") as f: 
3     lines = f.readlines() 
4     x=[] 
5     y=[] 
6     for line in lines: 
7         if re.search('E-002',line): 
8             x.append(float(line.replace("\r\n","").split(",")[0])) 
9             y.append(float(line.replace("\r\n","").split(",")[1]))

同样,以列表形式输出 x 和 y 前3个元素用于检验:

>>> [2.4e-08, 2.4000123e-08, 2.4000247e-08] 
[0.014349, 0.016005, 0.015455] # 数据读取正确

注:具体的数据读取方式要根据具体文本文件的特征决定,运用合适的方法才能得到更好的结果。

案例三:二维数据写入

很多时候,经过 process( ) 后的数据,需要备份留用或者供其他程序调用,因此,将处理后的数据写入文本文件也将是关键的一步。根据数据读入的经验,被读入的数据经常存储在 list 中,那么处理后数据也通常存储在 list 中,因此,以 list 的写入作为例子:

x = [1, 2, 3, 4]
y = [2.0, 4.0, 6.0, 8.0] # 参考数据

接下来就要考虑的是要以什么样的格式保存数据,为了更加直观的表现数据的关系,我们将 x,y 分别保存为一列,中间以空格键隔开,那么 csv.writer( ) 将是很好的工具:

1 xy = {} 
2 for i in range(len(x)): 
3     xy[x[i]] = y[i] 
4 with open(r"15.txt", 'wb') as f: 
5     writer = csv.writer(f,delimiter='\t') 
6     for x, y in xy.items(): 
7         writer.writerow([x, y]) 

为了同时保存 x 和 y 的对应值,这里把 x 和 y 写入字典,x 为键 (key), y 为 值 (value) ,xy 就是 x 和 y 构成的字典。保存后的数据格式如下所示:

1   2.0
2   4.0
3   6.0
4   8.0

案例四:多维数据写入

由于字典的键 (key) 和值 (value) 对应的特殊数据结构,写入二维数据较为方便,对于多维数据,我们就需要构建多维矩阵,或者列表与元组结合的方式录入:

x = [1, 2, 3, 4]
y = [2.0, 4.0, 6.0, 8.0]
z = [3.0, 6.0, 9.0, 12.0]

这里以三维数据为例子。同样,需要将 x,y,z 各一列写入到txt中:

1 xyz = [] 
2 for i in range(len(x)): 
3     xyz.append([x[i],y[i],z[i]]) 
4 with open(r"15.txt", 'wb') as f: 
5     writer = csv.writer(f,delimiter='\t') 
6     for x, y, z in xyz: 
7         writer.writerow([x, y, z]) 

这样,就可以很容易地得到需要的数据格式的文本文件:

1   2.0 3.0
2   4.0 6.0
3   6.0 9.0
4   8.0 12.0

我们已经提到了两种方法读取上述的数据,它们共同点是将数据存储在列表中,正如开头所说,列表在处理大量数据时是非常缓慢的。那么,我们就来看一看 numpy.genfromtxt 如何大显身手。

代码示例

为了得到我们需要的有用数据,我们有两个硬的要求: (1) 跳过表头信息;(2) 区分横纵坐标

import numpy as np
data = np.genfromtxt('waveform.txt',delimiter=',',skip_header=18)
**delimiter: the str used to separate data. 横纵坐标以 ',' 分割,因此给 delimiter 传入 ','。skip_header: ** the number of lines to skip at the beginning of the file. 有用数据是从19行开始的,因此给 skip_header 传入 18。
print data[0:3,0], data[0:3,1]

因为读入的是二维数据,因此利用 numpy 二维数据的切片方式 (Index slicing) 输出各自的前三个数据验证是否读取正确:

[  2.40000000e-08   2.40001230e-08   2.40002470e-08]
[ 0.014349  0.016005  0.015455]

对数据进行归一化处理后,调用 Matplotlib 画图命令,就可得到图像如下:

1 import matplotlib.pyplot as plt 
2 fig, axes = plt.subplots(figsize=(8,6)) 
3 axes.plot(x, y, 'r', linewidth=3) 
4 axes.set_xlabel('Time(ps)') 
5 axes.set_ylabel('Amplitude[a.u.]') 
6 fig.savefig("triangular.png", dpi=600)
triangular waveform

补充

numpy.genformtxt( ) 函数提供了众多的入参,实现不同格式数据的读取,详情可参考:numpy.genfromtxt
此外,numpy 中还提供了将数据存储为 CSV 格式的函数 numpy.savetxt( ),详情可参考:numpy.savetxt

转载于:https://www.cnblogs.com/ECJTUACM-873284962/p/8449346.html

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/453459.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

麻雀虽小,五脏俱全:分析CVS活动情况的小工具(有源码供学习)

最近开发团队发布的版本质量很成问题,追究起来有很多原因,其中之一是CVS的使用不合理, 于是想做个一小工具,分析CVS上每天的活动,以便掌握团队成员对CVS的使用情况。 也许有现成的开源项目可以完成这项任务&#xff…

php如果实现日历的制作,教大家制作简单的php日历

最近的一个项目中,需要将数据用日历方式显示,网上有很多的JS插件,后面为了自己能有更大的控制权,决定自己制作一个日历显示。如下图所示:一、计算数据1、new一个Calendar类2、初始化两个下拉框中的数据,年份…

Spark之 使用SparkSql操作mysql和DataFrame的Scala实现

通过读取文件转换成DataFrame数据写入到mysql中 package com.zy.sparksqlimport java.util.Propertiesimport org.apache.spark.SparkContext import org.apache.spark.rdd.RDD import org.apache.spark.sql.{DataFrame, Row, SparkSession} import org.apache.spark.sql.types…

web服务器之iis,apache,tomcat三者之间的比较

IIS-Apache-Tomcat的区别 IIS与Tomcat的区别 IIS是微软公司的Web服务器。主要支持ASP语言环境. Tomcat是Java Servlet 2.2和JavaServer Pages 1.1技术的标准实现,是基于Apache许可证下开发的SJP语言环境容器,严格得说不能算是一个WEB服务器,而是Apache服务适配器。 …

iOS CAGradientLayer颜色渐变

Gradient:本身就是梯度的意思,所以在这里就是作为渐变色来理解 CAGradientLayer用于处理渐变色的层结构CAGradientLayer的渐变色可以做隐式动画大部分情况下,CAGradientLayer时和CAShapeLayer配合使用,CAShapeLayer这里就不介绍了CAGradientL…

编程要养成的好习惯

1.- DRY: Don’t repeat yourself. DRY 是一个最简单的法则,也是最容易被理解的。但它也可能是最难被应用的(因为要做到这样,我们需要在泛型设计上做相当的努力,这并不是一件容易的事)。它意味着,当我们在…

flink整合java,Flink使用SideOutPut替换Split实现分流

基于apache flink的流处理实时模型44元包邮(需用券)去购买 >以前的数据分析项目(版本1.4.2),对从Kafka读取的原始数据流,调用split接口实现分流.新项目决定使用Flink 1.7.2,使用split接口进行分流的时候,发现接口被标记为depra…

虚机中访问外网;NAT中的POSTROUTING是怎么搞的?

看下docker中是怎么配置的网络 在虚机中访问外网:设定了qemu,在主机上添加路由:sudo iptables -t nat -I POSTROUTING -s 192.168.1.110 -j SNAT --to-source 192.168.0.108 设置了这句话就可以访问外网了。 设置了两个虚拟机: ta…

Fragment结合ViewPager之懒加载

什么是懒加载?为什么要用懒加载?### 1、什么是懒加载 懒加载就是当ViewPager和Fragment结合在一起使用时,Fragment呈现在用户面前时才加载数据,当其从未被呈现在用户面前时,不会执行加载数据的代码。这就是我所理解的懒…

WCF和webservice的区别

微软论坛的斑竹回答如下: 脑内:果然是高大上啊 1.WebService:严格来说是行业标准,不是技术,使用XML扩展标记语言来表示数据(这个是夸语言和平台的关键)。微 软的Web服务实现称为ASP.NET Web Ser…

职场不得不明白的十大定律

帕金森定律 美国著名历史学家诺斯古德•帕金森通过长期调查研究,写了一本名叫《帕金森定律》的书,他在书中阐述了机构人员膨胀的原因及后果:一个不称职的官员,可能有三条出路。第一是申请退职,把位子让给能干的人&am…

php控制器教程,laravel基础教程 -- 控制器

HTTP 控制器简介控制器允许你将相应的路由业务逻辑封装在控制器类中进行有效的管理,这样你不必将所有的路由逻辑集中到routes.php文件中,导致代码的臃肿与难以维护。所有的控制器类都被存储在app/Http/Controllers目录中.基本控制器一个基本的控制器应该…

org.apache.jasper.JasperException: Unable to compile class for JSP:

报错信息: org.apache.jasper.JasperException: Unable to compile class for JSP: An error occurred at line: 1 in the generated java file The type java.io.ObjectInputStream cannot be resolved. It is indirectly referenced from required .class filesSt…

i++和++i

关于自增自减运算,很多书籍没有把问题讲清楚,在C语言里是这样的: 1.后置运算:k表示先运算,后自加。 意思是遇到k了,我先把当前的k的值拿来参加运算,后面再去管它的自加。 那么,“后面”后到什么…

什么样的项目经历会让面试官眼前一亮

很多同学都问过我类似的问题: 咱们《C语言也能干大事》中讲的自己动手写windows优化大师、自己动手写计算器等东西只是写着玩的小玩具而已,这些能用来以后找工作时写到简历中的作品吗?看别人的简历写的“图书管理系统”、“教务选课系统”多有…

matlab采样频谱,Matlab对采样数据进行频谱分析

使用Matlab对采样数据进行频谱分析1、采样数据导入Matlab采样数据的导入至少有三种方法。第一就是手动将数据整理成Matlab支持的格式,这种方法仅适用于数据量比较小的采样。第二种方法是使用Matlab的可视化交互操作,具体操作步骤为:File --&g…

链表和顺序表的一些区别

顺序表与链表是非常基本的数据结构,它们可以被统称为线性表。 线性表(Linear List)是由 n(n≥0)个数据元素(结点)a[0],a[1],a[2]…,a[n-1] 组成的有限序列。…

ANCS推送简介

总体原理 ANCS通过蓝牙BLE 4.0实现,仅支持iPhone 4S及以上且系统版本在IOS 7以上的手机,同时在外设端需要支持蓝牙4.0协议。 1、外设端进行广播,手机打开蓝牙,搜索外设,连接外设,之后进行绑定(这…

好记性不如烂笔头,记录几个常用的Linux操作

作者:老王Shell公共函数库Linux系统里有一些公共的Shell函数库可供使用,最重要的是/etc/rc.d/init.d/functions,在/etc/init.d目录下有很多脚本都用到了这个函数库,里面提供了很多有用的方法,比如:killproc…

用matlab简单电路模型,基于MATLAB的电路模型仿真应用

基于MATLAB的电路模型仿真应用实验指导书一、实验目的1、掌握采用M文件及SIMULINK对电路进行仿真的方法。2、熟悉POWERSYSTEM BLOCKSET 模块集的调用、设置方法。3.进一步熟悉M脚本文件编写的方法和技巧。二、实验原理1、通过M文件实现电路仿真的一般仿真步骤为&…