TOML11_DEFINE_CONVERSION_NON_INTRUSIVE save files
keepitsimle opened this issue · comments
TOML11_DEFINE_CONVERSION_NON_INTRUSIVE
get value fine, but write values to file failed.
- toml11 version 3.7.0
- gcc version 9.4.0
here is code:
#include "toml.hpp"
#include <fstream>
#include <iostream>
namespace foo
{
class device
{
public:
int heart;
};
} // namespace foo
TOML11_DEFINE_CONVERSION_NON_INTRUSIVE(foo::device, heart)
int main()
{
auto file = toml::parse("cfg.toml");
auto f = toml::find<foo::device>(file, "device");
f.heart = 1;
std::ofstream ofs("cfg1.toml");
ofs << file;
ofs.close();
return 0;
}
and the cfg.toml
[device]
heart = 98
port = 1234
last cfg1.toml
[device]
port = 1234
heart = 98
Unfortunately, it does not work in that way.
You converted the data from toml::value
to foo::device
. This conversion inevitably copies the value because the converted types are not a reference nor pointer. You cannot modify the original through copied value because they are located in different regions of memory.
If you want to modify the value, you need to modify the original data. There are several ways to do that.
- you can modify the value directly.
int main()
{
auto file = toml::parse("cfg.toml");
file["device"]["heart"] = 1;
std::ofstream ofs("cfg1.toml");
ofs << file;
ofs.close();
return 0;
}
- you can take a non-const (mutable) reference to the data
int main()
{
auto file = toml::parse("cfg.toml");
auto& heart = toml::find(file, "device", "heart");
heart = 1;
std::ofstream ofs("cfg1.toml");
ofs << file;
ofs.close();
return 0;
}
- you can substitute modified
foo::device
to"device"
table.
int main()
{
auto file = toml::parse("cfg.toml");
auto f = toml::find<foo::device>(file, "device");
f.heart = 1;
file["device"] = f;
std::ofstream ofs("cfg1.toml");
ofs << file;
ofs.close();
return 0;
}
NOTE: The third example overwrites the whole device
table by foo::device
. Since foo::device
does not have port
member variable, file["device"] = f;
removes port
value in toml table.
thanks, it will be more convenient if i can do it in my way.