#include <AdaptInfo.h>

namespace AMDiS {

  void AdaptInfo::setScalContents(int newSize) {
    int oldSize = scalContents.getSize();

    if (newSize > oldSize) { 
      scalContents.resize(newSize);

      char number[5];
      for (int i = oldSize; i < newSize; i++) {
	sprintf(number, "[%d]", i);
	scalContents[i] = new ScalContent(name + std::string(number)); 
      }
    }
  }

  void AdaptInfo::serialize(std::ostream& out) {
    out << name << "\n";
    out.write(reinterpret_cast<const char*>(&maxSpaceIteration), sizeof(int));
    out.write(reinterpret_cast<const char*>(&spaceIteration), sizeof(int));
    out.write(reinterpret_cast<const char*>(&timestepIteration), sizeof(int));
    out.write(reinterpret_cast<const char*>(&maxTimestepIteration), sizeof(int));
    out.write(reinterpret_cast<const char*>(&timeIteration), sizeof(int));
    out.write(reinterpret_cast<const char*>(&maxTimeIteration), sizeof(int));
    out.write(reinterpret_cast<const char*>(&time), sizeof(double));
    out.write(reinterpret_cast<const char*>(&startTime), sizeof(double));
    out.write(reinterpret_cast<const char*>(&endTime), sizeof(double));
    out.write(reinterpret_cast<const char*>(&timestep), sizeof(double));
    out.write(reinterpret_cast<const char*>(&minTimestep), sizeof(double));
    out.write(reinterpret_cast<const char*>(&maxTimestep), sizeof(double));
    out.write(reinterpret_cast<const char*>(&timestepNumber), sizeof(int));
    out.write(reinterpret_cast<const char*>(&nTimesteps), sizeof(int));
    out.write(reinterpret_cast<const char*>(&solverIterations), sizeof(int));
    out.write(reinterpret_cast<const char*>(&maxSolverIterations), sizeof(int));
    out.write(reinterpret_cast<const char*>(&solverTolerance), sizeof(double));
    out.write(reinterpret_cast<const char*>(&solverResidual), sizeof(double));
    int size = scalContents.getSize();
    out.write(reinterpret_cast<const char*>(&size), sizeof(int));
    for (int i = 0; i < size; i++) {
      out.write(reinterpret_cast<const char*>(&(scalContents[i]->est_sum)), 
		sizeof(double));
      out.write(reinterpret_cast<const char*>(&(scalContents[i]->est_t_sum)), 
		sizeof(double));
      out.write(reinterpret_cast<const char*>(&(scalContents[i]->est_max)),
		sizeof(double));
      out.write(reinterpret_cast<const char*>(&(scalContents[i]->est_t_max)),
		sizeof(double));
      out.write(reinterpret_cast<const char*>(&(scalContents[i]->spaceTolerance)), 
		sizeof(double));
      out.write(reinterpret_cast<const char*>(&(scalContents[i]->timeTolerance)), 
		sizeof(double));
      out.write(reinterpret_cast<const char*>(&(scalContents[i]->timeErrLow)), 
		sizeof(double));
      out.write(reinterpret_cast<const char*>(&(scalContents[i]->coarsenAllowed)),
		sizeof(int));
      out.write(reinterpret_cast<const char*>(&(scalContents[i]->refinementAllowed)),
		sizeof(int));
      out.write(reinterpret_cast<const char*>(&(scalContents[i]->refineBisections)),
		sizeof(int));
      out.write(reinterpret_cast<const char*>(&(scalContents[i]->coarseBisections)),
		sizeof(int));
    }
  }

  void AdaptInfo::deserialize(std::istream& in) {
    in >> name;
    in.get();   // because of std::endl in serialization

    in.read(reinterpret_cast<char*>(&maxSpaceIteration), sizeof(int));
    in.read(reinterpret_cast<char*>(&spaceIteration), sizeof(int));
    in.read(reinterpret_cast<char*>(&timestepIteration), sizeof(int));
    in.read(reinterpret_cast<char*>(&maxTimestepIteration), sizeof(int));
    in.read(reinterpret_cast<char*>(&timeIteration), sizeof(int));
    in.read(reinterpret_cast<char*>(&maxTimeIteration), sizeof(int));
    in.read(reinterpret_cast<char*>(&time), sizeof(double));
    in.read(reinterpret_cast<char*>(&startTime), sizeof(double));
    in.read(reinterpret_cast<char*>(&endTime), sizeof(double));
    in.read(reinterpret_cast<char*>(&timestep), sizeof(double));
    in.read(reinterpret_cast<char*>(&minTimestep), sizeof(double));
    in.read(reinterpret_cast<char*>(&maxTimestep), sizeof(double));
    in.read(reinterpret_cast<char*>(&timestepNumber), sizeof(int));
    in.read(reinterpret_cast<char*>(&nTimesteps), sizeof(int));
    in.read(reinterpret_cast<char*>(&solverIterations), sizeof(int));
    in.read(reinterpret_cast<char*>(&maxSolverIterations), sizeof(int));
    in.read(reinterpret_cast<char*>(&solverTolerance), sizeof(double));
    in.read(reinterpret_cast<char*>(&solverResidual), sizeof(double));
    int size;
    in.read(reinterpret_cast<char*>(&size), sizeof(int));
    scalContents.resize(size);    
    for (int i = 0; i < size; i++) {
      //      if (!scalContents[i]) {
	char number[5];
	sprintf(number, "[%d]", i);
	scalContents[i] = new ScalContent(name + std::string(number)); 
	//    }
      in.read(reinterpret_cast<char*>(&(scalContents[i]->est_sum)), 
	      sizeof(double));
      in.read(reinterpret_cast<char*>(&(scalContents[i]->est_t_sum)), 
	      sizeof(double));
      in.read(reinterpret_cast<char*>(&(scalContents[i]->est_max)),
	      sizeof(double));
      in.read(reinterpret_cast<char*>(&(scalContents[i]->est_t_max)),
	      sizeof(double));
      in.read(reinterpret_cast<char*>(&(scalContents[i]->spaceTolerance)), 
	      sizeof(double));
      in.read(reinterpret_cast<char*>(&(scalContents[i]->timeTolerance)), 
	      sizeof(double));
      in.read(reinterpret_cast<char*>(&(scalContents[i]->timeErrLow)), 
	      sizeof(double));
      in.read(reinterpret_cast<char*>(&(scalContents[i]->coarsenAllowed)),
	      sizeof(int));
      in.read(reinterpret_cast<char*>(&(scalContents[i]->refinementAllowed)),
	      sizeof(int));
      in.read(reinterpret_cast<char*>(&(scalContents[i]->refineBisections)),
	      sizeof(int));
      in.read(reinterpret_cast<char*>(&(scalContents[i]->coarseBisections)),
	      sizeof(int));
    }    
  }

}