Qt 学习之路 :文本文件读写
上一章我们介绍了有关二进制文件的读写。二进制文件比较小巧,却不是人可读的格式。而文本文件是一种人可读的文件。为了操作这种文件,我们需要使用QTextStream
类。QTextStream
和QDataStream
的使用类似,只不过它是操作纯文本文件的。另外,像 XML、HTML 这种,虽然也是文本文件,可以由QTextStream
生成,但 Qt 提供了更方便的 XML 操作类,这里就不包括这部分内容了。
QTextStream
会自动将 Unicode 编码同操作系统的编码进行转换,这一操作对开发人员是透明的。它也会将换行符进行转换,同样不需要自己处理。QTextStream
使用 16 位的QChar
作为基础的数据存储单位,同样,它也支持 C++ 标准类型,如 int 等。实际上,这是将这种标准类型与字符串进行了相互转换。
QTextStream
同QDataStream
的使用基本一致,例如下面的代码将把“The answer is 42”写入到 file.txt 文件中:
1
2
3
4
5
|
QFile data("file.txt");
if (data.open(QFile::WriteOnly | QIODevice::Truncate)) {
QTextStream out(&data);
out << "The answer is " << 42;
}
|
这里,我们在open()
函数中增加了QIODevice::Truncate
打开方式。我们可以从下表中看到这些打开方式的区别:
枚举值 | 描述 |
QIODevice::NotOpen |
未打开 |
QIODevice::ReadOnly |
以只读方式打开 |
QIODevice::WriteOnly |
以只写方式打开 |
QIODevice::ReadWrite |
以读写方式打开 |
QIODevice::Append |
以追加的方式打开,新增加的内容将被追加到文件末尾 |
QIODevice::Truncate |
以重写的方式打开,在写入新的数据时会将原有数据全部清除,游标设置在文件开头。 |
QIODevice::Text |
在读取时,将行结束符转换成 \n;在写入时,将行结束符转换成本地格式,例如 Win32 平台上是 \r\n |
QIODevice::Unbuffered |
忽略缓存 |
我们在这里使用了QFile::WriteOnly | QIODevice::Truncate
,也就是以只写并且覆盖已有内容的形式操作文件。注意,QIODevice::Truncate
会直接将文件内容清空。
虽然QTextStream
的写入内容与QDataStream
一致,但是读取时却会有些困难:
1
2
3
4
5
6
7
|
QFile data("file.txt");
if (data.open(QFile::ReadOnly)) {
QTextStream in(&data);
QString str;
int ans = 0;
in >> str >> ans;
}
|
在使用QDataStream
的时候,这样的代码很方便,但是使用了QTextStream
时却有所不同:读出的时候,str 里面将是 The answer is 42,ans 是 0。这是因为以文本形式写入数据,是没有数据之间的分隔的。还记得我们前面曾经说过,使用QDataStream
写入的时候,实际上会在要写入的内容前面,额外添加一个这段内容的长度值。而文本文件则没有类似的操作。因此,使用文本文件时,很少会将其分割开来读取,而是使用诸如QTextStream::readLine()
读取一行,使用QTextStream::readAll()
读取所有文本这种函数,之后再对获得的QString
对象进行处理。
默认情况下,QTextStream
的编码格式是 Unicode,如果我们需要使用另外的编码,可以使用
1
|
stream.setCodec("UTF-8");
|
这样的函数进行设置。
另外,为方便起见,QTextStream
同std::cout
一样提供了很多描述符,被称为 stream manipulators。因为文本文件是供人去读的,自然需要良好的格式(相比而言,二进制文件就没有这些问题,只要数据准确就可以了)。这些描述符是一些函数的简写,我们可以从文档中找到:
描述符 | 等价于 |
bin |
setIntegerBase(2) |
oct |
setIntegerBase(8) |
dec |
setIntegerBase(10) |
hex |
setIntegerBase(16) |
showbase |
setNumberFlags(numberFlags() | ShowBase) |
forcesign |
setNumberFlags(numberFlags() | ForceSign) |
forcepoint |
setNumberFlags(numberFlags() | ForcePoint) |
noshowbase |
setNumberFlags(numberFlags() & ~ShowBase) |
noforcesign |
setNumberFlags(numberFlags() & ~ForceSign) |
noforcepoint |
setNumberFlags(numberFlags() & ~ForcePoint) |
uppercasebase |
setNumberFlags(numberFlags() | UppercaseBase) |
uppercasedigits |
setNumberFlags(numberFlags() | UppercaseDigits) |
lowercasebase |
setNumberFlags(numberFlags() & ~UppercaseBase) |
lowercasedigits |
setNumberFlags(numberFlags() & ~UppercaseDigits) |
fixed |
setRealNumberNotation(FixedNotation) |
scientific |
setRealNumberNotation(ScientificNotation) |
left |
setFieldAlignment(AlignLeft) |
right |
setFieldAlignment(AlignRight) |
center |
setFieldAlignment(AlignCenter) |
endl |
operator<<('\n') 和flush() |
flush |
flush() |
reset |
reset() |
ws |
skipWhiteSpace() |
bom |
setGenerateByteOrderMark(true) |
这些描述符只是一些函数的简写。例如,我们想要输出 12345678 的二进制形式,那么可以直接使用
1
|
out << bin << 12345678;
|
就可以了。这等价于
1
2
|
out.setIntegerBase(2);
out << 12345678;
|
更复杂的,如果我们想要舒服 1234567890 的带有前缀、全部字母大写的十六进制格式(0xBC614E),那么只要使用
1
|
out << showbase << uppercasedigits << hex << 12345678;
|
即可。
不仅是QIODevice
,QTextStream
也可以直接把内容输出到QString
。例如
1
2
|
QString str;
QTextStream(&str) << oct << 31 << " " << dec << 25 << endl;
|
这提供了一种简单的处理字符串内容的方法。
Qt 学习之路 :文本文件读写的更多相关文章
- Qt 学习之路 2(37):文本文件读写
Qt 学习之路 2(37):文本文件读写 豆子 2013年1月7日 Qt 学习之路 2 23条评论 上一章我们介绍了有关二进制文件的读写.二进制文件比较小巧,却不是人可读的格式.而文本文件是一种人可读 ...
- Qt 学习之路 2(36):二进制文件读写
Qt 学习之路 2(36):二进制文件读写 豆子 2013年1月6日 Qt 学习之路 2 20条评论 在上一章中,我们介绍了有关QFile和QFileInfo两个类的使用.我们提到,QIODevice ...
- 《Qt 学习之路 2》目录
<Qt 学习之路 2>目录 <Qt 学习之路 2>目录 豆子 2012年8月23日 Qt 学习之路 2 177条评论 <Qt 学习之路 2>目录 序 Qt ...
- Qt 学习之路 2(72):线程和事件循环
Qt 学习之路 2(72):线程和事件循环 <理解不清晰,不透彻> -- 有需求的话还需要进行专题学习 豆子 2013年11月24日 Qt 学习之路 2 34条评论 前面一章我 ...
- Qt 学习之路 2(64):使用 QJsonDocument 处理 JSON
Home / Qt 学习之路 2 / Qt 学习之路 2(64):使用 QJsonDocument 处理 JSON Qt 学习之路 2(64):使用 QJsonDocument 处理 JSON 豆子 ...
- Qt 学习之路 2(60):使用 DOM 处理 XML
Qt 学习之路 2(60):使用 DOM 处理 XML 豆子 2013年8月3日 Qt 学习之路 2 9条评论 DOM 是由 W3C 提出的一种处理 XML 文档的标准接口.Qt 实现了 DO ...
- Qt 学习之路 2(52):使用拖放
Qt 学习之路 2(52):使用拖放 豆子 2013年5月21日 Qt 学习之路 2 17条评论 拖放(Drag and Drop),通常会简称为 DnD,是现代软件开发中必不可少的一项技术.它提供了 ...
- Qt 学习之路 2(39):遍历容器
Qt 学习之路 2(39):遍历容器 豆子 2013年1月16日 Qt 学习之路 2 29条评论 上一节我们大致了解了有关存储容器的相关内容.对于所有的容器,最常用的操作就是遍历.本章我们将详细了解有 ...
- Qt 学习之路 2(35):文件
Qt 学习之路 2(35):文件 豆子 2013年1月5日 Qt 学习之路 2 12条评论 文件操作是应用程序必不可少的部分.Qt 作为一个通用开发库,提供了跨平台的文件操作能力.从本章开始,我们来了 ...
- Qt 学习之路 2(17):文件对话框
Home / Qt 学习之路 2 / Qt 学习之路 2(17):文件对话框 Qt 学习之路 2(17):文件对话框 豆子 2012年9月24日 Qt 学习之路 2 85条评论 在前面的章节中 ...
随机推荐
- STM32随记
定时器(Timer): 分为高级,通用,基本三种. M3:8个 高级:TIM1,TM8 通用:TIM2~TIM5 基本:TIM6,TIM7 M0:8个 高级:TIM1 通用:TIM2,TIM3,TIM ...
- phpcms v9使用GET调用指定id文章内容、页面数据方法
不知道大家有没有相同的体会?在使用Phpcms V9建站调用数据的时候,基础的数据用默认的模板的调用语句就好了,但复杂不常见的数据怎么调用呢?我们技术可能会研究半天,怀着探索的精神不断尝试.孜孜不倦. ...
- CoreProfiler/NanoProfiler
使用CoreProfiler/NanoProfiler实现跨平台&应用的整合性能调试 摘要 NanoProfiler是一个开源.NET性能调试类库,CoreProfiler是其.NET Cor ...
- Spring MVC小结1
由于最近刚开始学Spring MVC,所以来讲一下自己的理解. 首先进行环境配置: 1.jdk 2.myeclipse 3.tomcat 4.maven 配置maven的时候出现了一个小的问题,JAV ...
- 10个WordPress增强型编辑器大检阅
Wordpress之所以优秀不在于其本身,而在于无数的插件开发者和性能优化人员.使用过Wordpress的人都知道,WP本身的编辑器极其简陋,就连简单的表格编辑也没有,可能吧这篇文章将介绍一些免费的增 ...
- [BZOJ 1112] [POI2008] 砖块Klo 【区间K大】
题目链接:BZOJ - 1112 题目分析 枚举每一个长度为k的连续区间,求出这个区间的最优答案,更新全局答案. 可以发现,这个区间的所有柱子最终都变成这k个数的中位数时最优,那么我们就需要查询这个区 ...
- 学习VI的强文,新工作需要呀
http://www.gentoo.org/doc/zh_cn/vi-guide.xml :set nu//用于给文本加行号的. :set nocompatible //启用 vi 兼容模式,一般是给 ...
- 能分析压缩的日志,且基于文件输入的PYTHON代码实现
确实感觉长见识了. 希望能坚持,并有多的时间用来分析这些思路和模式. #!/usr/bin/python import sys import gzip import bz2 from optparse ...
- 子元素div高度不确定时父div高度如何自适应
粘自:http://www.jb51.net/css/110652.html 在最外层div加以下样式 height:100%; overflow:hidden; 其它方法: Div即父容器不根据内容 ...
- jsp的url后跟中文参数传参出现乱码
①重新编码:String urlParam= request.getParameter("urlParam"); urlParam= new String(urlParam.ge ...