我正在尝试使用 C++ 实现 MCTS,并且为了保存(在文件中)模拟播放的所有动作,我实现了一个“arbrecontigu”类来构造一个向量element
(其中包含我们 MCTS 中使用的信息:' Brix' 是例如我们游戏的名称),来自不完整且不平衡的二叉树。
MC 算法本身工作得很好,但是当我的二叉树的高度在 30 左右时,我得到了一个“错误分配”错误//values.reserve(tailletab);
同时,我可以初始化一个大小为 2^100 的向量int
而不会出错,所以我有点困惑......
// arbrecontigu.h
#ifndef ARBRECONTIGU_H
#define ARBRECONTIGU_H
#include <iostream>
#include <vector>
#include <string>
#include <fstream>
#include <cstdlib>
#include <sstream>
#include <math.h>
#include "arbrebin.h"
#include "../brix.hh"
struct element{
int value;
int iterations;
bool isnull;
Brix brix;
};
class ArbreContigu
{
private:
std::vector<element> file_to_vector(const std::string & filename);
std::vector<std::string> explode(const std::string & str, char x);
public:
std::vector<element> values;
ArbreContigu(const std::string & filename);
ArbreContigu(Binarytree const& b); // a définir (! sans recursivité)
std::vector<element> getvalues() const {return values;}
void to_csv(std::string const & filename);
};
#endif // ARBRECONTIGU_H
// arbrecontigu.cpp
#include "arbrecontigu.h"
#include <queue>
ArbreContigu::ArbreContigu(const std::string &filename)
{
values = file_to_vector(filename);
}
ArbreContigu::ArbreContigu(const Binarytree &b)
{
if (!b.isnull()) {
std::queue<const Binarytree::Node * > qb;
std::queue<size_t> qi;
qi.push(1);
qb.push(&b.getNodeConst());
size_t tabsize = static_cast<size_t>(std::pow(2,(b.hauteur()+1)));
//values.reserve(tailletab);
for (size_t i = 0;i<tabsize;++i)
{
values.push_back({0,0,true,Brix()});
}
while (!qb.empty()) {
const Binarytree::Node * nodeb = qb.front();
size_t i = qi.front();
qb.pop();
qi.pop();
values[i-1] = {nodeb->getVal(),nodeb->getVal(),false,nodeb->getCoup()};
if (!nodeb->leftIsNull()) {
qb.push(&nodeb->getLeftConst());
qi.push(i*2);
}
if (!nodeb->rightIsNull()) {
qb.push(&nodeb->getRightConst());
qi.push(i*2+1);
}
}
}
}
std::vector<std::string> ArbreContigu::explode(const std::string &str, char x)
{
std::vector<std::string> result;
std::istringstream in(str);
std::string token;
while(getline(in, token, x))
result.push_back(token);
return result;
}
std::vector<element> ArbreContigu::file_to_vector(const std::string &filename)
{
std::vector<element> values;
std::string line;
std::ifstream file(filename);
if(!file){
std::cout << "Impossible d'ouvrir le fichier !" << std::endl;}
else {
while(getline(file,line)){
element elem;
std::vector<std::string> vect_temp = explode(line,';');
if (vect_temp.size() == 1)
elem.isnull = true;
else
{
elem.isnull = false;
elem.value = std::stoi(vect_temp[0]);
elem.iterations = std::stoi(vect_temp[1]);
elem.brix.setAx(std::stoi(vect_temp[2]));
elem.brix.setOx(std::stoi(vect_temp[3]));
elem.brix.setAo(std::stoi(vect_temp[4]));
elem.brix.setOo(std::stoi(vect_temp[5]));
elem.brix.setDefinie(vect_temp[6]=="1" ? true : false);
}
values.push_back(elem);
}
}
file.close();
return values;
}
void ArbreContigu::to_csv(std::string const & filename){
std::fstream file;
file.open (filename, std::fstream::trunc | std::fstream::out );
if(!file)
std::cout << "Impossible d'ouvrir le fichier !" << std::endl;
else {
for (auto elements : values){
if (elements.isnull)
file << "N" << std::endl;
else {
file << elements.value << ";"
<< elements.iterations << ";"
<< elements.brix.getAx() << ";"
<< elements.brix.getOx() << ";"
<< elements.brix.getAo() << ";"
<< elements.brix.getOo() << ";"
<<elements.brix.getDefinie() << std::endl;
}
}
}
file.close();
}
例 1
#include <vector>
#include <math.h>
#include <iostream>
int main (){
std::vector<int> a;
a.reserve(pow(2,100));
std::cout<<"..sucess.."<<std::endl;
}
是的,这对于 2 ^ 100 来说也很奇怪,但是这段代码让我很成功,没有任何错误
但是在我的转换构造函数中,我不能做超过 2 ^ 20 的储备