yaml-cpp 0.5 emiter yaml文件读取和写回

.环境

ubuntu16+qt5.6.2+yaml-cpp0.5.3

.前提

http://blog.csdn.net/azhuty/article/details/68485569yaml文件来源)

https://github.com/jbeder/yaml-cpp/wiki/How-To-Emit-YAML(更多细节可以参考他的wiki

环境都已经弄好了

.开工

在项目pro中添加yaml的静态库链接

LIBS    +=/home/Desktop/yaml-cpp-release-0.5.3/build/libyaml-cpp.a
INCLUDEPATH+= -l/home/Desktop/yaml-cpp-release-0.5.3/include/yaml-cpp -l

yaml文件格式

subscribers:  
  - name:        "Default task"  
    topic:       "input/cmd_default_check"  
    timeout:     0.5  
    priority:    1  
    short_desc:  "Default controller"  
  - name:        "Navigation stack"  
    topic:       "input/cmd_serial_navi"  
    timeout:     1.0  
    priority:    3  
    short_desc:  "Navigation controller"  
publisher:       "output/cmd_vel" 

然后qmake

头文件

#ifndef YAML_READ_WRITE_H
#define YAML_READ_WRITE_H
#include<yaml-cpp/yaml.h>
#include<QString>

class yaml_read_write
{
public:
    yaml_read_write();
    YAML::Node DataMem;
    YAML::Emitter emitter;
    bool dump();
    bool setFilePath(std::string path);
private:
    std::string filename;
//    template <typedef T>
//    T getValue(T);


};

#endif // YAML_READ_WRITE_H

DataMem:缓存的读取yaml数据

emitter用来写回文件的

filename具体的文件路径

yaml_cpp

#include "yaml_read_write.h"
#include<fstream>
yaml_read_write::yaml_read_write()
{

}


bool yaml_read_write::dump()
{
    if(!filename.empty())
    {
        std::ofstream fout(filename);
        fout << emitter.c_str();
        return true;
    }
    return false;
}

bool yaml_read_write::setFilePath(std::string path)
{
    filename=path;
    if(!filename.empty())
    {
       DataMem=YAML::LoadFile(filename);
    }
    if (DataMem.IsNull())
            return false;
    return true;
}

读取部分

读取一个简单的数据

    ui->setupUi(this);
    yaml_read_write *yaml=new yaml_read_write();
   if( yaml->setFilePath("yaml.yml"))
   {
       YAML::Node Name=yaml->DataMem["subscribers"];
       std::string name=Name[0]["name"].as<std::string>();
       ui->lineEdit->setText(QString::fromStdString(name));
} 

在这边需要注意你读取的结构一定要合理

DataMem相当于一个多维的数组你不能读取数组中不存在的项目会被异常


throw TypedBadConversion<std::string>(node.Mark());

实际上name已经是key[subscribers]value


对于Map的读写

此时NameNode的内容如下Name是一个Map


对于list的读写

std::vector<int>v=Name[0]["list"].as<std::vector<int>>();(此时list里面都是int类型的数据其他也可以根据需要修改)

与需要上传的结果一致


写入文件部分

对原有数据进行修改


    yaml->DataMem["subscribers"][0]["list"][4]=55;
       yaml->DataMem["subscribers"][0]["list"][4]=11;   
       yaml->dump();
       


这边有一个好玩的地方

对列表进行修改的话,如果下标越界包括像这种yaml->DataMem["subscribers"][0]["list"]["Key"]="say"

会从sequenceturn to map


感觉大大棒棒哒(这一拨骚走位,服气)



改回来尝试另一种越狱



记住list现在长这样

 yaml->DataMem["subscribers"][0]["list"][5]=55;
 yaml->dump();
       

yaml->DataMem["subscribers"][0]["list"][5]=55;当超出list下标+1的时候也会自动变成map

追加新的内容

追加一个map

 yaml->emitter<<yaml->DataMem;
 yaml->emitter<<YAML::BeginMap;
 yaml->emitter<<YAML::Key<<"name";
 yaml->emitter<<YAML::Value<<"lululu";
 yaml->emitter<<YAML::Key<<"sex";
 yaml->emitter<<YAML::Value<<"girl&man";
 yaml->emitter<<YAML::EndMap;
 yaml->dump();

       std::vector <int> squares;
       squares.push_back(1);
       squares.push_back(4);
       squares.push_back(9);
       squares.push_back(16);

       std::map <std::string, int> ages;
       ages["Daniel"] = 26;
       ages["Jesse"] = 24;
       yaml->emitter << YAML::BeginSeq;
       yaml->emitter << YAML::Flow << squares;
       yaml->emitter << ages;
       yaml->emitter << YAML::EndSeq;

       yaml->dump();


在已有节点下追加内容

如何在subscribes节点下面插入格式一模一样的比较困难,目前只能找到一种替代方法

利用之前使用过的namenode(特别注意,这里面的Node都是浅复制,使用一片MEM对一个copy进行操作的话就会造成其他也改变)


       Name[2]["name"]="ll";
       Name[2]["ip"]="118";

总结

1.throwTypedBadConversion<std::string>(node.Mark());这个异常一般都是对yaml结构没有理解清楚,不是其他错误,是缓存里面没有这个KEY

2.注意Node是浅复制,对它数据进行操作的时候需要小心,会影响到其他指向相同内存的Node节点,所以慎用新的Node节点来记录同一份DataMem






  • 1
    点赞
  • 5
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值