赞
踩
.ini 文件是Initialization File的缩写,即初始化文件。
INI文件被用来对操作系统或特定程序初始化或进行参数设置,以实现不同用户的要求。
一般不用直接编辑这些.ini文件,应用程序的图形界面即可操作以实现相同的功能。
在Qt中可以使用QSetting类来实现ini文件的读取和写入。
ini文件主要有节(section)、键(key)、键值(value)部分组成。
节 (section) 用方括号括起来,单独占一行,例如:
[section]
键(key)又名属性(property),单独占一行用等号连接键名和键值,例如:
name=value
例子
- [Section1 Name]
- KeyName1=value1
- KeyName2=value2
- ...
- [Section2 Name]
- KeyName21=value21
- KeyName22=value22
其中:[Section1 Name]用来表示一个段落。
因为INI文件可能是项目中共用的,所以使用[Section Name]段名来区分不同用途的参数区。
注意:使用分号表示(;)。在分号后面的文字,直到该行结尾都全部为注解。
Qt通过QSettings类读写ini文件。
QSettings的存储设置,每个设置都由一个QString和一个QVariant组成,
QString指定设置的名称(键),QVariant存储与该键关联的数据。
- 头文件:QSetting.h
- QSetting读写ini文件的步骤为:
- * 通过路径名称打开文件并设定为ini文件格式
- * 读/写数据
- * 关闭文件,删除句柄
QSettings::Format有两种:
QSettings::NativeFormat在windows平台可以读写windows注册表;
QSettings::IniFormat可以读写ini格式的配置文件。
- // 根据ini文件路径新建QSettings类
- QSettings m_IniFile = new QSettings("ini文件的路径", QSettings::IniFormat);
- //通过setValue函数将键值对放在相对于的节下面
- m_IniFile->setValue( "节名" + "/" + "键名", "键对应的值");
- delete m_IniFile;
-
- 分组写入
- //根据ini文件路径新建QSettings类
- QSettings m_IniFile = new QSettings("ini文件的路径", QSettings::IniFormat);
- m_IniFile ->beginGroup("节名"); // 设置当前节名,代表以下的操作都是在这个节中
- m_IniFile->setValue( "键名", "键对应的值"); // 因为上面设置了节了,这里不在需要把节名写上去
- m_IniFile.endGroup(); // 结束当前节的操作
- delete m_IniFile;
- //Qt中使用QSettings类读写ini文件
- //QSettings构造函数的第一个参数是ini文件的路径,第二个参数表示针对ini文件,第三个参数可以缺省
- QSettings *configIniWrite = new QSettings("config.ini", QSettings::IniFormat);
- //向ini文件中写入内容,setValue函数的两个参数是键值对
- //向ini文件的第一个节写入内容,ip节下的第一个参数
- configIniWrite->setValue("/con/ip", "192.168.0.1");
- //向ini文件的第一个节写入内容,ip节下的第二个参数
- configIniWrite->setValue("/con/name", "aa");
- //向ini文件的第二个节写入内容,port节下的第一个参数
- configIniWrite->setValue("port/open", "2222");
- configIniWrite->setValue("port/ports", "2222,111,33,444");
- //写入完成后删除指针
- delete configIniWrite;
-
- 生成文件 config.ini
- [con]
- ip=192.168.0.1
- name=aa
-
- [port]
- open=2222
- ports="2222,111,33,444"
- //通过Value函数将节下相对应的键值读取出来
- QString value = m_IniFile->Value( "节名" + "/" + "键名").toString;
- //打开文件并指定为ini格式
- QSettings* configIni = new QSettings(file_path, QSettings::IniFormat);
- QString qTemp = "";
- //读指定节点的指定数据,其中“Log”为节点,save_days为具体数据项
- logDays = configIni->value("Log/save_days").toInt();
- qTemp = configIni->value("Log/print_debug").toString();
- printDbgLog = qTemp.compare("true", Qt::CaseInsensitive) == 0 ? true : false;
- //删除指针,此处未关联父对象,必须手动删除,否则有内存泄露风险
- delete configIni;
-
- 分组读取
- settings.beginGroup("Setting");
- QString strName = settings.value("Name").toString();
- int nVersion = settings.value("Version").toInt();
- settings.endGroup();
- //Name:Qt Creator Version:5
-
- settings.beginGroup("User");
- QString strUserName = settings.value("UserName").toString();
- QString strPassword = settings.value("Password").toString();
- settings.endGroup();
- //UserName:WangL Password:123456
- [conn]
- name=aaa
- ip="192.168.1.10"
- auto_con=1
- speed=50
- joints=0.000,-13.959,2.2,83.3,0.000,18.000,-30.000
- tcp_offset= 133.4,0.0,0.0,0.0,0.0,-10.0
-
- 读配置文件
- QSettings setting("config.ini",QSettings::IniFormat);
- setting.setIniCodec("utf-8");// 解决乱码
- QString name =setting.value("conn/name").toString();
- int speed =setting.value("conn/speed").toInt();
-
- qDebug() << name;
- qDebug() << speed;
-
- 输出:
- "aaa"
- 50
在实际使用中,QSettings的写操作在某些情况下会丢失数据。
尤其在嵌入式Liunx环境中,通过断电方式关机,更容易丢失数据。
原因分析:
1,Qt的保存机制是先写到一个临时文件中,然后定时去同步到磁盘,所以不能实时生效。
2,setValue函数设置指定KEY的值,若该值已存在则替换先前的值,但不立即回写文件。
3,QSettings类的sync方法并不能立刻同步到磁盘上,需要使用系统sync或syncFlushFileBuffers进行同步。
解决措施:
1,在写完后调用QSettings的函数settings.sync();
2,调用Linux系统的shell命令system("sync");
- #include <QtCore/QtCore>
- #include <QSettings>
- #include <QFile>
- #include <QDebug>
- #include <QTextCodec>
-
- void ConfigSetting(void)
- {
- //文件路径+文件名
- QString fileName = QCoreApplication::applicationDirPath() + "/Config.ini";
- //创建配置目标,输入文件路径,文件格式
- QSettings *setting = new QSettings(fileName , QSettings::IniFormat);
- //设置文件编码,配置文件中使用中文时,这是必须的,否则乱码
- setting->setIniCodec(QTextCodec::codecForName("UTF-8"));
- // 判断文件是否存在
- if(QFile::exists(fileName)){// 文件存在,读出配置项
- // 这里的setting->value的第二参数,是配置项缺省值,即当读取的配置项不存在时,读取该值
- // User是配置组,name和age是配置项
- QString name = setting->value("User/name", "张三").toString();
- int age = setting->value("User/age", 30).toInt();
- }else {// 文件不存在,写入配置项,生成配置文件
- setting->setValue("User/name", "张三");
- setting->setValue("User/age", 30);
- // setValue只是把配置项写入了缓冲区,若要写入文件,还需执行同步
- // 不同步,无法写入文件,无法生成文件
- setting->sync();
- system("sync");//将内核缓冲写入文件(磁盘)
- }
- delete setting;
- }
QSetting中的key值与项目标题如果用中文的话,打开会是乱码。
QSetting中变量值中如果包含分号,则值字符串需要用双引号(" ")来引用,
否则取值时候,只会取值到该变量第一个分号之前的内容。
使用QSettings 将 float 类型的数据写入到ini时
float dx = 1.0;
sParamSetting->setValue("SectionData/d_correct",dx);
ini文件中内容如下:
d_correct=@Variant(\0\0\0\x87\xbeH\xb4\x39)
这是因为 QSettings在写float类型时有点问题,可以将float强制转化为double就可以了。
也可以将变量设置为double dx = 1.0;
sParamSetting->setValue("SectionData/d_correct", (double)(sCorrectParam.lcz_correct));
资料来源
https://www.cnblogs.com/qianxiaoPro/p/15623881.html
https://www.cnblogs.com/xiangtingshen/p/11145974.html
https://blog.csdn.net/yinyuchen1/article/details/75093895
https://www.cnblogs.com/mzy-google/p/5162107.html
https://blog.csdn.net/qq_33485434/article/details/80483883
https://blog.csdn.net/weixin_40583088/article/details/104660595
Copyright © 2003-2013 www.wpsshop.cn 版权所有,并保留所有权利。