1 /*! 2 * \file tfel-check/src/Column.cxx 3 * 4 * Created on: 23 mai 2013 5 * Author: rp238441 6 * \copyright Copyright (C) 2006-2018 CEA/DEN, EDF R&D. All rights 7 * reserved. 8 * This project is publicly released under either the GNU GPL Licence 9 * or the CECILL-A licence. A copy of thoses licences are delivered 10 * with the sources of TFEL. CEA or EDF may also distribute this 11 * project under specific licensing conditions. 12 */ 13 14 #include<sstream> 15 #include<stdexcept> 16 #include<algorithm> 17 #include"TFEL/Raise.hxx" 18 #include"TFEL/Math/Evaluator.hxx" 19 #include"TFEL/Check/Column.hxx" 20 21 namespace tfel{ 22 23 namespace check{ 24 25 static std::vector<double> eval(const tfel::utilities::TextData & d,const std::string & f)26 eval(const tfel::utilities::TextData& d, 27 const std::string& f){ 28 struct Variable{ 29 unsigned short p; 30 std::vector<double> values; 31 }; 32 auto matches=[](const std::string& vn){ 33 if(vn.size()<2){ 34 return false; 35 } 36 if(vn[0]!='$'){ 37 return false; 38 } 39 auto p = std::begin(vn)+1; 40 for(;p!=vn.end();++p){ 41 const char c = *p; 42 if(!((c>='0')&&(c<='9'))){ 43 return false; 44 } 45 } 46 return true; 47 }; 48 auto convert = [](const std::string& vn){ 49 auto p = std::begin(vn)+1; 50 unsigned short value{0}; 51 for(;p!=vn.end();++p){ 52 const char c = *p; 53 raise_if(!((c>='0')&&(c<='9')), 54 "tfel::check::eval::convert: " 55 "invalid input '"+vn+"'"); 56 value*=10; 57 value+=c-'0'; 58 } 59 return value; 60 }; 61 tfel::math::Evaluator e{f}; 62 std::vector<Variable> variables; 63 unsigned short p = 0u; 64 for(const auto& v : e.getVariablesNames()){ 65 raise_if(!matches(v),"tfel::check::eval: undeclared " 66 "variable '"+v+"'"); 67 variables.push_back(Variable{p,d.getColumn(convert(v))}); 68 ++p; 69 } 70 if(variables.empty()){ 71 return d.getColumn(convert(f)); 72 } 73 std::vector<double> r; 74 r.resize(variables[0].values.size()); 75 for(std::vector<double>::size_type i=0;i!=r.size();++i){ 76 for(const auto& v:variables){ 77 e.setVariableValue(v.p,v.values[i]); 78 } 79 r[i] = e.getValue(); 80 } 81 return r; 82 } // end of eval 83 84 Column::Column(Column&&) = default; 85 Column::Column(const Column&) = default; 86 Column& Column::operator=(Column&&) = default; 87 Column& Column::operator=(const Column&) = default; 88 Column(const int n)89 Column::Column(const int n) 90 : num(n), 91 byName(false) { 92 this->name = std::to_string(this->num); 93 } 94 Column(std::string n)95 Column::Column(std::string n) 96 : name(std::move(n)), 97 num(0), 98 byName(true) 99 {} 100 getName() const101 std::string Column::getName() const { 102 return this->name; 103 } 104 getValues()105 const std::vector<double>& Column::getValues() { 106 return this->values; 107 } clearValues()108 void Column::clearValues() { 109 this->values.clear(); 110 } 111 resizeValues(std::vector<double>::size_type size)112 void Column::resizeValues(std::vector<double>::size_type size) { 113 this->values.resize(size); 114 } 115 setValue(unsigned pos,double value)116 void Column::setValue(unsigned pos, double value) { 117 this->values.at(pos) = value; 118 } 119 setFilename(std::string file)120 void Column::setFilename(std::string file) { 121 this->f = file; 122 this->data = std::make_shared<tfel::utilities::TextData>(file,"alcyone"); 123 if (this->byName) { 124 const auto& l = data->getLegends(); 125 if(std::find(l.begin(),l.end(),this->name)!=l.end()){ 126 this->num = data->findColumn(name); 127 this->values = this->data->getColumn(this->num); 128 } else { 129 this->values = eval(*(this->data),this->name); 130 return; 131 } 132 } else { 133 this->data->getColumn(this->values, this->num); 134 } 135 } 136 getFilename() const137 const std::string& Column::getFilename() const { 138 return this->f; 139 } 140 141 const std::shared_ptr<tfel::utilities::TextData> getData() const142 Column::getData() const { 143 return this->data; 144 } 145 146 Column::~Column() = default; 147 148 } // end of namespace check 149 150 } // end of namespace tfel 151